In Webpack dev middleware, for configs that target Node, just run a 'watch' compiler (since Node isn't going to fetch the modules via HTTP anyway)

This commit is contained in:
SteveSandersonMS
2016-09-27 17:51:56 +01:00
parent 2241c55a90
commit 7b227229b3

View File

@@ -43,7 +43,7 @@ function attachWebpackDevMiddleware(app: any, webpackConfig: webpack.Configurati
} }
}); });
webpackConfig.plugins = webpackConfig.plugins || []; webpackConfig.plugins = [].concat(webpackConfig.plugins || []); // Be sure not to mutate the original array, as it might be shared
webpackConfig.plugins.push( webpackConfig.plugins.push(
new webpack.HotModuleReplacementPlugin() new webpack.HotModuleReplacementPlugin()
); );
@@ -79,6 +79,13 @@ function attachWebpackDevMiddleware(app: any, webpackConfig: webpack.Configurati
} }
} }
function beginWebpackWatcher(webpackConfig: webpack.Configuration) {
const compiler = webpack(webpackConfig);
compiler.watch({ /* watchOptions */ }, (err, stats) => {
// The default error reporter is fine for now, but could be customized here in the future if desired
});
}
export function createWebpackDevServer(callback: CreateDevServerCallback, optionsJson: string) { export function createWebpackDevServer(callback: CreateDevServerCallback, optionsJson: string) {
const options: CreateDevServerOptions = JSON.parse(optionsJson); const options: CreateDevServerOptions = JSON.parse(optionsJson);
@@ -93,15 +100,6 @@ export function createWebpackDevServer(callback: CreateDevServerCallback, option
webpackConfigArray = [webpackConfigArray as webpack.Configuration]; webpackConfigArray = [webpackConfigArray as webpack.Configuration];
} }
// Check that at least one of the configurations specifies a publicPath. Those are the only ones we'll
// enable middleware for, and if there aren't any, you must be making a mistake.
const webpackConfigsWithPublicPath = webpackConfigArray
.filter(webpackConfig => (webpackConfig.output.publicPath || '').trim() !== '');
if (webpackConfigsWithPublicPath.length === 0) {
callback('To use the Webpack dev server, you must specify a value for \'publicPath\' on the \'output\' section of your webpack.config.', null);
return;
}
const enableHotModuleReplacement = options.suppliedOptions.HotModuleReplacement; const enableHotModuleReplacement = options.suppliedOptions.HotModuleReplacement;
const enableReactHotModuleReplacement = options.suppliedOptions.ReactHotModuleReplacement; const enableReactHotModuleReplacement = options.suppliedOptions.ReactHotModuleReplacement;
if (enableReactHotModuleReplacement && !enableHotModuleReplacement) { if (enableReactHotModuleReplacement && !enableHotModuleReplacement) {
@@ -116,16 +114,30 @@ export function createWebpackDevServer(callback: CreateDevServerCallback, option
const listener = app.listen(suggestedHMRPortOrZero, () => { const listener = app.listen(suggestedHMRPortOrZero, () => {
try { try {
// For each webpack config that specifies a public path, add webpack dev middleware for it // For each webpack config that specifies a public path, add webpack dev middleware for it
webpackConfigsWithPublicPath.forEach(webpackConfig => { const normalizedPublicPaths: string[] = [];
attachWebpackDevMiddleware(app, webpackConfig, enableHotModuleReplacement, enableReactHotModuleReplacement); webpackConfigArray.forEach(webpackConfig => {
if (webpackConfig.target === 'node') {
// For configs that target Node, it's meaningless to set up an HTTP listener, since
// Node isn't going to load those modules over HTTP anyway. It just loads them directly
// from disk. So the most relevant thing we can do with such configs is just write
// updated builds to disk, just like "webpack --watch".
beginWebpackWatcher(webpackConfig);
} else {
// For configs that target browsers, we can set up an HTTP listener, and dynamically
// modify the config to enable HMR etc. This just requires that we have a publicPath.
const publicPath = (webpackConfig.output.publicPath || '').trim();
if (!publicPath) {
throw new Error('To use the Webpack dev server, you must specify a value for \'publicPath\' on the \'output\' section of your webpack config (for any configuration that targets browsers)');
}
normalizedPublicPaths.push(removeTrailingSlash(publicPath));
attachWebpackDevMiddleware(app, webpackConfig, enableHotModuleReplacement, enableReactHotModuleReplacement);
}
}); });
// Tell the ASP.NET app what addresses we're listening on, so that it can proxy requests here // Tell the ASP.NET app what addresses we're listening on, so that it can proxy requests here
callback(null, { callback(null, {
Port: listener.address().port, Port: listener.address().port,
PublicPaths: webpackConfigsWithPublicPath.map(webpackConfig => PublicPaths: normalizedPublicPaths
removeTrailingSlash(getPath(webpackConfig.output.publicPath))
)
}); });
} catch (ex) { } catch (ex) {
callback(ex.stack, null); callback(ex.stack, null);