diff --git a/lib/plugin.js b/lib/plugin.js index 92e7910..d0b7964 100644 --- a/lib/plugin.js +++ b/lib/plugin.js @@ -1,53 +1,30 @@ "use strict"; -const RawSource = require("webpack-sources").RawSource; - const log = require("./logger").log; -const RuleSet = require("./rule-set"); -const CompiledChunks = require("./compiled-chunks"); -const publicPath = require("./public-path"); -const TemplatedAssets = require("./templated-assets"); +const tap = require("./tap"); class Plugin { constructor(opts) { - const options = opts || {}; + let options = opts || {}; if (!options.rules) { log("No rules specified. No templated chunks will be outputted."); log(options); + options.rules = []; } - - this.rules = RuleSet.from(options.rules); + this.pluginName = "TemplatedAssetsWebpackPlugin"; + this.pluginOptions = options; } apply(compiler) { - compiler.plugin("emit", (compilation, callback) => { - const chunks = new CompiledChunks( - compilation.chunks, - compilation.assets, - publicPath(compilation) - ).chunks; - - new TemplatedAssets(chunks, this.rules) - .process() - .then(templatedAssets => { - templatedAssets.forEach(asset => { - if (!asset.emitAsset) return; - try { - compilation.assets[asset.filename] = new RawSource(asset.source); - } catch (e) { - throw new Error( - `Failed to include asset ${JSON.stringify( - asset - )} to compilation. -${e.message}` - ); - } - }); - - callback(); - }) - .catch(log); - }); + if (!!compiler.hooks) { + compiler.hooks.emit.tapAsync(this.pluginName, (compilation, callback) => + tap(this.pluginOptions, compilation, callback) + ); + } else { + compiler.plugin("emit", (compilation, callback) => + tap(this.pluginOptions, compilation, callback) + ); + } } } diff --git a/lib/tap.js b/lib/tap.js new file mode 100644 index 0000000..bde5356 --- /dev/null +++ b/lib/tap.js @@ -0,0 +1,37 @@ +const RawSource = require("webpack-sources").RawSource; + +const RuleSet = require("./rule-set"); +const CompiledChunks = require("./compiled-chunks"); +const publicPath = require("./public-path"); +const TemplatedAssets = require("./templated-assets"); +const log = require("./logger").log; + +function tap(options, compilation, callback) { + const rules = RuleSet.from(options.rules); + const chunks = new CompiledChunks( + compilation.chunks, + compilation.assets, + publicPath(compilation) + ).chunks; + + new TemplatedAssets(chunks, rules) + .process() + .then(templatedAssets => { + templatedAssets.forEach(asset => { + if (!asset.emitAsset) return; + try { + compilation.assets[asset.filename] = new RawSource(asset.source); + } catch (e) { + throw new Error( + `Failed to include asset ${JSON.stringify(asset)} to compilation. +${e.message}` + ); + } + }); + + callback(); + }) + .catch(log); +} + +module.exports = tap; diff --git a/package.json b/package.json index 1bbee3a..713c738 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "templated-assets-webpack-plugin", - "version": "1.2.0", + "version": "1.3.0", "description": "webpack plugin for creating assets to be used with server rendered web frameworks.", "main": "index.js", "dependencies": { diff --git a/test/plugin-init-test.js b/test/plugin-init-test.js index dfdcae9..b1c9fc7 100644 --- a/test/plugin-init-test.js +++ b/test/plugin-init-test.js @@ -2,18 +2,15 @@ import test from "ava"; import Plugin from "../lib/plugin"; test("fallback to empty rule set", t => { - const ruleSet = new Plugin().rules; - const rules = ruleSet.rules; - + const { rules } = new Plugin().pluginOptions; t.true(Array.isArray(rules)); t.is(rules.length, 0); }); test("init rules", t => { - const ruleSet = new Plugin({ + const { rules } = new Plugin({ rules: [{ name: "an-entry" }] - }).rules; - const rules = ruleSet.rules; + }).pluginOptions; t.true(Array.isArray(rules)); t.is(rules.length, 1);