简体   繁体   English

对factor-bundle的部分包进行一些操作

[英]make some operations on factor-bundle's partial bundles

I am using gulp with browserify and factor-bundle. 我正在使用浏览器和factor-bundle。 I have the following code: 我有以下代码:

b = browserify({
        entries: [ 'a.js', 'b.js'],
        plugin: [ [ 'factor-bundle', { outputs: [ 'build/a.js', 'build/b.js' ] } ] ]
    })
    .bundle()
    .pipe(source('bundle.js'))
    .pipe(buffer())
    .pipe(gulp.dest('/build/common'));

I want to pipe some actions (like uglify, bundle-collapser or other job) on the parial bundles ('build/a.js' and 'build/b.js'). 我想在parial包('build / a.js'和'build / b.js')上管理一些动作(比如uglify,bundle-collapser或其他工作)。 I tried to use the method described on the factor-bundle's page: 我尝试使用factor-bundle页面上描述的方法:

b.plugin('factor-bundle', { outputs: [ write('x'), write('y') ] });
function write (name) {
    return concat(function (body) {
        console.log('// ----- ' + name + ' -----');
        console.log(body.toString('utf8'));
    });
}

But I don't understand the write() method and don't know how to perform uglification and how to gulp.dest the result. 但我不理解write()方法,也不知道如何执行uglification以及如何gulp.dest结果。
Any idea? 任何的想法? explanation? 说明?

The write() method returns a writable stream that allows you to pipe bundles generated by the factor-bundle plugin through further downstream transformations. write()方法返回一个可写流,允许您通过进一步的下游转换来管理由factor-bundle插件生成的包。

For instance, your write() method may look something like this: 例如,您的write()方法可能如下所示:

var path = require('path');
var file = require('gulp-file');
var sourcemaps = require('gulp-sourcemaps');

function write (filepath) {    
    return concat(function (content) {        
        // create new vinyl file from content and use the basename of the
        // filepath in scope as its basename.
        return file(path.basename(filepath), content, { src: true })
        // uglify content
        .pipe(uglify())
        // write content to build directory
        .pipe(gulp.dest('./build/scripts'))        
    });
}

And you would use it like this: 你会像这样使用它:

browserify({
    entries: [ 'a.js', 'b.js'],
    plugin: [ [ 'factor-bundle', { outputs: [ write('a.js'), write('b.js') ] } ] ]
})
.bundle()
.pipe(write('common.js'))
// Could have use these instead, but it wouldn't be as DRY.
// .pipe(source('common.js'))
// .pipe(uglify())
// .pipe(gulp.dest('./build/scripts'))

Using the factor-bundle plugin affects the output of browserify after .bundle() is called. 在调用.bundle()之后,使用factor-bundle插件会影响browserify的输出。 Normally, it would generate bundles as readable streams mapping to each of your entry files, then you would be able to apply further transformations to them. 通常,它会生成捆绑包作为映射到每个条目文件的可读流,然后您就可以对它们应用进一步的转换。

Instead you will get a single readable stream that contains a bundle with the shared common modules from the supplied entry files, which I have called common.js on the example above. 相反,您将获得一个可读的流,其中包含来自提供的条目文件的共享公共模块的捆绑包,我在上面的示例中称为common.js Then you need to handle the transfomations of the readable streams that map to each entry file separately. 然后,您需要分别处理映射到每个条目文件的可读流的转换。

In the example above I have added writable streams to the outputs array, arranged in the same order as my entry files, which receive their respective bundle as readable stream and apply further transformations to them 在上面的示例中,我将可写流添加到输出数组,按照与我的条目文件相同的顺序排列,它们将各自的包接收为可读流并对它们应用进一步的转换

You could also leverage the factor.pipeline event : 您还可以利用factor.pipeline 事件

var b = browserify({ ... });

b.on('factor.pipeline', function (id, pipeline) {
    pipeline.get('wrap').push(write(id));
});

b.plugin(factor);

return b.bundle().pipe(write('common.js'));

I think it is worth noting that applying further downstream work to the outputs is completely detached from the pipeline. 我认为值得注意的是,将更多下游工作应用于产出完全脱离了管道。 So if you were using gulp and returned the stream from browserify, the task would have completed prematurely because it would still be performing operations on the entry files. 因此,如果您使用gulp并从browserify返回流,则该任务将过早完成,因为它仍将对条目文件执行操作。 I haven't run into issues with this yet. 我还没有遇到过这方面的问题。

Hope this helps. 希望这可以帮助。

This is a bit old, but it might be usefull to someone else. 这有点旧,但它可能对其他人有用。 The answer above from @Christian helped me, but i had to solve the issue of the task completion. @Christian的上述答案帮助了我,但我必须解决任务完成的问题。 I did it by adding a counter for opened streams, and calling the task callback once they are all closed. 我通过为打开的流添加一个计数器,并在它们全部关闭后调用任务回调来完成它。

gulp.task('build:js:compile', function(cb) {

const apps  = getAllJavascriptFilesPaths(); // this returns an array of full path to the js files i want to bundle
const dist  = 'dist'; // the output path

const files = [];
const streams = [];
let openedStreams = 0;

// We use browserify factor-bundle to get the shared code in a separated js file, and not in all apps files
// The write function here handles the post processing of each browserified app by returning a writable stream
// We check the number of opened streams, and call the callback once they are all closed, to be sure the task is
// complete
function write(filepath) {
    openedStreams++;
    return concat(function (content) {
        // create new vinyl file from content and use the basename of the
        // filepath in scope as its basename.
        return file(path.basename(filepath), content, { src: true })
            .pipe(uglify())
            .pipe(gulp.dest(dist))
            .on('finish', function () {
                openedStreams--;
                if (openedStreams == 0) {
                    cb();
                }
            });
    });
}

apps.forEach(function (file) {
    files.push(file);
    streams.push(write(file)));
});

browserify(files)
    .plugin(factor, { outputs: streams })
    .transform("babelify", {presets: 'babel-preset-env'})
    .bundle()
    .pipe(write('common.js'));
});

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM