Skip to content
This repository was archived by the owner on Feb 7, 2022. It is now read-only.
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -238,6 +238,30 @@ function notify() {

run(configPath, options, notify);
```

You can pass a notify callback for every webpack watch callback as well.
```javascript
var run = require('parallel-webpack').run,
configPath = require.resolve('./webpack.config.js'),
options = {/*...*/};

let qeueu = [];
run(configPath, options, () => {
console.log('[webpack-parallel] every configuration has been compiled. I will not be invoked anymore');
}, (list, i) => {
if (qeueu.length === 0) {
qeueu = list.map(Number);
}
console.log(`[webpack-parallel] configuration #${i} is compiled in watch mode.`);
if (qeueu.includes(i)) {
qeueu.splice(qeueu.indexOf(i), 1);
if (qeueu.length === 0) {
console.log(`[webpack-parallel] all configurations(${list.join(',')}) were compiled in watch mode.`);
}
}
});
```

**NOTE:** In watch mode notify callback provided with Node.js API will run **only once**
when all of the builds are finished.

Expand Down
11 changes: 7 additions & 4 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,14 @@ function notSilent(options) {
return !options.json;
}

function startFarm(config, configPath, options, runWorker, callback) {
function startFarm(config, configPath, options, runWorker, doneCallback, watchCallback) {
config = Array.isArray(config) ? config : [config];
options = options || {};

// When in watch mode and a callback is provided start IPC server to invoke callback
// once all webpack configurations have been compiled
if (options.watch) {
startWatchIPCServer(callback, Object.keys(config));
startWatchIPCServer(doneCallback, watchCallback, Object.keys(config));
}

if(notSilent(options)) {
Expand Down Expand Up @@ -69,14 +69,16 @@ function startFarm(config, configPath, options, runWorker, callback) {
* on build error
* @param {Function} [callback] A callback to be invoked once the build has
* been completed
* @param {Function} [watchCallback] A callback to be invoked on each configuration build complete in watch mode.
* @return {Promise} A Promise that is resolved once all builds have been
* created
*/
function run(configPath, options, callback) {
function run(configPath, options, callback, watchCallback) {
var config,
argvBackup = process.argv,
farmOptions = assign({}, options);
options = options || {};

if(options.colors === undefined) {
options.colors = chalk.supportsColor;
}
Expand Down Expand Up @@ -122,7 +124,8 @@ function run(configPath, options, callback) {
configPath,
options,
Promise.promisify(workers),
callback
callback,
watchCallback
).error(function(err) {
if(notSilent(options)) {
console.log('%s Build failed after %s seconds', chalk.red('[WEBPACK]'), chalk.blue((Date.now() - startTime) / 1000));
Expand Down
10 changes: 6 additions & 4 deletions src/__tests__/watchDoneHandler.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,9 @@ describe('watchDoneHandler', () => {
it('should stop server and invoke callback', () => {
let configIndices = [0, 1];
let callback = jest.fn();
watchDoneHandler(callback, ipc, configIndices, 0);
watchDoneHandler(callback, ipc, configIndices, 1);
let dontStop = false;
watchDoneHandler(callback, ipc, configIndices, dontStop, 0);
watchDoneHandler(callback, ipc, configIndices, dontStop, 1);
expect(configIndices).toEqual([]);
expect(callback).toHaveBeenCalled();
expect(ipc.server.stop).toHaveBeenCalled();
Expand All @@ -32,8 +33,9 @@ describe('watchDoneHandler', () => {
it('should stop server', () => {
let configIndices = [0, 1];
let callback = jest.fn();
watchDoneHandler(null, ipc, configIndices, 0);
watchDoneHandler(null, ipc, configIndices, 1);
let dontStop = false;
watchDoneHandler(null, ipc, configIndices, dontStop, 0);
watchDoneHandler(null, ipc, configIndices, dontStop, 1);
expect(configIndices).toEqual([]);
expect(ipc.server.stop).toHaveBeenCalled();
});
Expand Down
6 changes: 4 additions & 2 deletions src/watchDoneHandler.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,13 @@
* Handler for done event
* @param data - the configuration index of the completed webpack run
*/
module.exports = function watchDoneHandler(callback, ipc, configIndices, data) {
module.exports = function watchDoneHandler(callback, ipc, configIndices, dontStop, data) {
// Once every configuration has completed once, stop the server and invoke the callback
configIndices.splice(configIndices.indexOf(data), 1);
if (!configIndices.length) {
ipc.server.stop();
if (!dontStop) {
ipc.server.stop();
}

if (typeof callback === 'function') {
callback();
Expand Down
29 changes: 26 additions & 3 deletions src/watchModeIPC.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,21 +7,31 @@ module.exports = {
/**
* Start IPC server and listens for 'done' message from child processes
* @param {any} callback - callback invoked once 'done' has been emitted by each confugration
* @param {Function} watchCallback - callback invoked on every webpack compile in watch mode
* @param {any} configIndices - array indices of configuration
*/
startWatchIPCServer: function startWatchIPCServer(callback, configIndices) {
startWatchIPCServer: function startWatchIPCServer(callback, watchCallback, configIndices) {
ipc.config.id = serverName;
ipc.config.retry = 3;
ipc.config.silent = true;

var dontStopServer = !!watchCallback;

ipc.serve(
function() {
ipc.server.on(
'done',
watchDoneHandler.bind(this, callback, ipc, configIndices)
watchDoneHandler.bind(this, callback, ipc, configIndices, dontStopServer)
);
if (watchCallback) {
ipc.server.on(
'watchCallback',
watchCallback.bind(null, [].concat(configIndices))
)
}
}
);

ipc.server.start();
},

Expand All @@ -40,5 +50,18 @@ module.exports = {
ipc.of.webpack.emit('done', index);
}
);
}
},

notifyIPCWatchCallback: function notifyIPCWatchCallback(index) {
ipc.config.id = serverName + index;
ipc.config.stopRetrying = 3;
ipc.config.silent = true;

ipc.connectTo(
serverName,
function() {
ipc.of.webpack.emit('watchCallback', index);
}
);
},
}
11 changes: 8 additions & 3 deletions src/webpackWorker.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ var Promise = require('bluebird'),
chalk = require('chalk'),
loadConfigurationFile = require('./loadConfigurationFile').default,
notifyIPCWatchCompileDone = require('./watchModeIPC').notifyIPCWatchCompileDone,
notifyIPCWatchCallback = require('./watchModeIPC').notifyIPCWatchCallback,
presetToOptions = require('webpack/lib/Stats').presetToOptions;
/**
* Choose the most correct version of webpack, prefer locally installed version,
Expand Down Expand Up @@ -135,10 +136,14 @@ module.exports = function(configuratorFileName, options, index, expectedConfigLe
if(!watch) {
process.removeListener('SIGINT', shutdownCallback);
done(null, options.stats ? JSON.stringify(stats.toJson(outputOptions), null, 2) : '');
} else if (!hasCompletedOneCompile) {
notifyIPCWatchCompileDone(index);
hasCompletedOneCompile = true;
} else {
notifyIPCWatchCallback(index);
if (!hasCompletedOneCompile) {
notifyIPCWatchCompileDone(index);
hasCompletedOneCompile = true;
}
}

};
if(!silent) {
console.log('%s Started %s %s', chalk.blue('[WEBPACK]'), watch ? 'watching' : 'building', chalk.yellow(getAppName(webpackConfig)));
Expand Down