diff --git a/bin/packages/build.js b/bin/packages/build.js index 5750b8b1c30ffe..e4e7c7355bf113 100755 --- a/bin/packages/build.js +++ b/bin/packages/build.js @@ -5,8 +5,9 @@ const path = require( 'path' ); const glob = require( 'fast-glob' ); const ProgressBar = require( 'progress' ); const workerFarm = require( 'worker-farm' ); +const { Readable } = require( 'stream' ); -let files = process.argv.slice( 2 ); +const files = process.argv.slice( 2 ); /** * Path to packages directory. @@ -17,7 +18,13 @@ const PACKAGES_DIR = path.resolve( __dirname, '../../packages' ); let onFileComplete = () => {}; -if ( ! files.length ) { +let stream; + +if ( files.length ) { + stream = new Readable( { encoding: 'utf8' } ); + files.forEach( ( file ) => stream.push( file ) ); + stream.push( null ); +} else { const bar = new ProgressBar( 'Build Progress: [:bar] :percent', { width: 30, incomplete: ' ', @@ -26,7 +33,7 @@ if ( ! files.length ) { bar.tick( 0 ); - files = glob.sync( [ + stream = glob.stream( [ `${ PACKAGES_DIR }/*/src/**/*.js`, `${ PACKAGES_DIR }/*/src/*.scss`, ], { @@ -37,7 +44,15 @@ if ( ! files.length ) { onlyFiles: true, } ); - bar.total = files.length; + // Pause to avoid data flow which would begin on the `data` event binding, + // but should wait until worker processing below. + // + // See: https://nodejs.org/api/stream.html#stream_two_reading_modes + stream + .pause() + .on( 'data', ( file ) => { + bar.total = files.push( file ); + } ); onFileComplete = () => { bar.tick(); @@ -46,14 +61,16 @@ if ( ! files.length ) { const worker = workerFarm( require.resolve( './build-worker' ) ); -let complete = 0; +let ended = false, + complete = 0; -files.forEach( ( file ) => { - worker( file, () => { +stream + .on( 'data', ( file ) => worker( file, () => { onFileComplete(); - if ( ++complete === files.length ) { + if ( ended && ++complete === files.length ) { workerFarm.end( worker ); } - } ); -} ); + } ) ) + .on( 'end', () => ended = true ) + .resume();