Add events `html-webpack-plugin-before-html-processing`, `html-webpack-plugin-after-html-processing`, `html-webpack-plugin-after-emit`

This commit is contained in:
Jan Nicklas 2016-01-07 11:14:23 +01:00 committed by Jan Nicklas
parent df441b8b83
commit b4363a8575
4 changed files with 198 additions and 13 deletions

View File

@ -263,3 +263,20 @@ plugins: [
]
```
Events
------
To allow other plugins to alter the html this plugin executes the following events:
* `html-webpack-plugin-before-html-processing`
* `html-webpack-plugin-after-html-processing`
* `html-webpack-plugin-after-emit`
Usage:
```
compilation.plugin('html-webpack-plugin-before-html-processing', function(htmlPluginData, callback) {
htmlPluginData.html += 'The magic footer';
callback();
});
```

View File

@ -97,10 +97,30 @@ HtmlWebpackPlugin.prototype.apply = function(compiler) {
return typeof compilationResult !== 'function' ? compilationResult :
self.executeTemplate(compilationResult, chunks, assets, compilation);
})
// Allow plugins to change the html before assets are injected
.then(function(html) {
return new Promise(function(resolve){
var pluginArgs = {html: html, assets: assets, plugin: self};
compilation.applyPluginsAsyncWaterfall('html-webpack-plugin-before-html-processing', pluginArgs,
function() {
resolve(pluginArgs.html);
});
});
})
.then(function(html) {
// Add the stylesheets, scripts and so on to the resulting html
return self.postProcessHtml(html, assets);
})
// Allow plugins to change the html after assets are injected
.then(function(html) {
return new Promise(function(resolve){
var pluginArgs = {html: html, assets: assets, plugin: self};
compilation.applyPluginsAsyncWaterfall('html-webpack-plugin-after-html-processing', pluginArgs,
function() {
resolve(pluginArgs.html);
});
});
})
.catch(function(err) {
// In case anything went wrong the promise is resolved
// with the error message and an error is logged
@ -118,7 +138,11 @@ HtmlWebpackPlugin.prototype.apply = function(compiler) {
return html.length;
}
};
callback();
// Let other plugins know that we are done:
compilation.applyPluginsAsyncWaterfall('html-webpack-plugin-after-emit', {
html: compilation.assets[self.options.filename],
plugin: self
}, callback);
});
});
};
@ -424,21 +448,12 @@ HtmlWebpackPlugin.prototype.htmlWebpackPluginAssets = function(compilation, chun
* Injects the assets into the given html string
*/
HtmlWebpackPlugin.prototype.injectAssetsIntoHtml = function(html, assets) {
var chunks = Object.keys(assets.chunks);
// Gather all css and script files
var styles = [];
var scripts = [];
chunks.forEach(function(chunkName) {
styles = styles.concat(assets.chunks[chunkName].css);
scripts.push(assets.chunks[chunkName].entry);
});
// Turn script files into script tags
scripts = scripts.map(function(scriptPath) {
var scripts = assets.js.map(function(scriptPath) {
return '<script src="' + scriptPath + '"></script>';
});
// Turn css files into link tags
styles = styles.map(function(stylePath) {
var styles = assets.css.map(function(stylePath) {
return '<link href="' + stylePath + '" rel="stylesheet">';
});
// Injections

View File

@ -1,6 +1,6 @@
{
"name": "html-webpack-plugin",
"version": "2.2.0",
"version": "2.3.0",
"description": "Simplifies creation of HTML files to serve your webpack bundles",
"main": "index.js",
"files": [

View File

@ -551,6 +551,159 @@ describe('HtmlWebpackPlugin', function() {
['Public path is https://cdn.com'], null, done);
});
it('fires the html-webpack-plugin-before-html-processing event', function(done) {
var eventFired = false;
var examplePlugin = {
apply: function(compiler) {
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-before-html-processing', function(object, callback) {
eventFired = true;
callback();
});
});
}
};
testHtmlPlugin({
entry: {
app: path.join(__dirname, 'fixtures/index.js')
},
output: {
path: OUTPUT_DIR,
filename: '[name]_bundle.js'
},
plugins: [
new HtmlWebpackPlugin(),
examplePlugin
]
},[], null, function() {
expect(eventFired).toBe(true);
done();
});
});
it('fires the html-webpack-plugin-after-html-processing event', function(done) {
var eventFired = false;
var examplePlugin = {
apply: function(compiler) {
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-after-html-processing', function(object, callback) {
eventFired = true;
callback();
});
});
}
};
testHtmlPlugin({
entry: {
app: path.join(__dirname, 'fixtures/index.js')
},
output: {
path: OUTPUT_DIR,
filename: '[name]_bundle.js'
},
plugins: [
new HtmlWebpackPlugin(),
examplePlugin
]
},[], null, function() {
expect(eventFired).toBe(true);
done();
});
});
it('fires the html-webpack-plugin-after-emit event', function(done) {
var eventFired = false;
var examplePlugin = {
apply: function(compiler) {
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-after-emit', function(object, callback) {
eventFired = true;
callback();
});
});
}
};
testHtmlPlugin({
entry: {
app: path.join(__dirname, 'fixtures/index.js')
},
output: {
path: OUTPUT_DIR,
filename: '[name]_bundle.js'
},
plugins: [
new HtmlWebpackPlugin(),
examplePlugin
]
},[], null, function() {
expect(eventFired).toBe(true);
done();
});
});
it('allows to modify the html during html-webpack-plugin-after-html-processing event', function(done) {
var eventFired = false;
var examplePlugin = {
apply: function(compiler) {
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-after-html-processing', function(object, callback) {
eventFired = true;
object.html += 'Injected by plugin';
callback();
});
});
}
};
testHtmlPlugin({
entry: {
app: path.join(__dirname, 'fixtures/index.js')
},
output: {
path: OUTPUT_DIR,
filename: '[name]_bundle.js'
},
plugins: [
new HtmlWebpackPlugin(),
examplePlugin
]
},['Injected by plugin'], null, function() {
expect(eventFired).toBe(true);
done();
});
});
it('allows to modify the html during html-webpack-plugin-before-html-processing event', function(done) {
var eventFired = false;
var examplePlugin = {
apply: function(compiler) {
compiler.plugin('compilation', function(compilation) {
compilation.plugin('html-webpack-plugin-before-html-processing', function(object, callback) {
eventFired = true;
object.assets.js.push('funky-script.js');
object.html += 'Injected by plugin';
callback();
});
});
}
};
testHtmlPlugin({
entry: {
app: path.join(__dirname, 'fixtures/index.js')
},
output: {
path: OUTPUT_DIR,
filename: '[name]_bundle.js'
},
plugins: [
new HtmlWebpackPlugin(),
examplePlugin
]
},['Injected by plugin', '<script src="funky-script.js"'], null, function() {
expect(eventFired).toBe(true);
done();
});
});
it('works with commons chunk plugin', function(done) {
testHtmlPlugin({
debug: true,