Skip to content

Commit

Permalink
feat: improve ssr
Browse files Browse the repository at this point in the history
  • Loading branch information
jantimon committed Feb 19, 2021
1 parent e5036c8 commit 73d2a66
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 5 deletions.
17 changes: 13 additions & 4 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -123,12 +123,20 @@ class HtmlWebpackPlugin {
return Promise.reject(new Error('The child compilation didn\'t provide a result'));
}
// The LibraryTemplatePlugin stores the template result in a local variable.
// To extract the result during the evaluation this part has to be removed.
if (source && source.indexOf('HTML_WEBPACK_PLUGIN_RESULT') >= 0) {
// By adding it to the end the value gets extracted during evaluation
if (source.indexOf('HTML_WEBPACK_PLUGIN_RESULT') >= 0) {
source += ';\nHTML_WEBPACK_PLUGIN_RESULT';
}
const templateWithoutLoaders = templateFilename.replace(/^.+!/, '').replace(/\?.+$/, '');
const vmContext = vm.createContext({ HTML_WEBPACK_PLUGIN: true, require: require, htmlWebpackPluginPublicPath: publicPath, ...global });
const vmContext = vm.createContext({
...global,
HTML_WEBPACK_PLUGIN: true,
require: require,
htmlWebpackPluginPublicPath:
publicPath,
URL: require('url').URL,
__filename: templateWithoutLoaders
});
const vmScript = new vm.Script(source, { filename: templateWithoutLoaders });
// Evaluate code and cast to string
let newSource;
Expand All @@ -147,7 +155,8 @@ class HtmlWebpackPlugin {
}

/**
* apply is called by the webpack main compiler during the start phase
* connect the html-webpack-plugin to the webpack compiler lifecycle hooks
*
* @param {import('webpack').Compiler} compiler
* @param {ProcessedHtmlWebpackOptions} options
* @param {HtmlWebpackPlugin} plugin
Expand Down
12 changes: 11 additions & 1 deletion lib/child-compiler.js
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,7 @@ class HtmlWebpackChildCompiler {
const webpack = mainCompilation.compiler.webpack;
const Compilation = webpack.Compilation;

const NodeTemplatePlugin = webpack.node.NodeTemplatePlugin;
const NodeTargetPlugin = webpack.node.NodeTargetPlugin;
const LoaderTargetPlugin = webpack.LoaderTargetPlugin;
const EntryPlugin = webpack.EntryPlugin;
Expand Down Expand Up @@ -103,6 +104,7 @@ class HtmlWebpackChildCompiler {
const childCompiler = mainCompilation.createChildCompiler(compilerName, outputOptions, [
// Compile the template to nodejs javascript
new NodeTargetPlugin(),
new NodeTemplatePlugin(),
new LoaderTargetPlugin('node'),
new webpack.library.EnableLibraryPlugin('var')
]);
Expand All @@ -114,10 +116,18 @@ class HtmlWebpackChildCompiler {

// Add all templates
this.templates.forEach((template, index) => {
new EntryPlugin(childCompiler.context, 'data:text/javascript,__webpack_public_path__ = htmlWebpackPluginPublicPath;', `HtmlWebpackPlugin_${index}-${this.id}`).apply(childCompiler);
new EntryPlugin(childCompiler.context, 'data:text/javascript,__webpack_public_path__ = __webpack_base_uri__ = htmlWebpackPluginPublicPath;', `HtmlWebpackPlugin_${index}-${this.id}`).apply(childCompiler);
new EntryPlugin(childCompiler.context, template, `HtmlWebpackPlugin_${index}-${this.id}`).apply(childCompiler);
});

// The templates are compiled and executed by NodeJS - similar to server side rendering
// Unfortunately this causes issues as some loaders require an absolute URL to support ES Modules
// The following config enables relative URL support for the child compiler
childCompiler.options.module = { ...childCompiler.options.module };
childCompiler.options.module.parser = { ...childCompiler.options.module.parser };
childCompiler.options.module.parser.javascript = { ...childCompiler.options.module.parser.javascript,
url: 'relative' };

this.compilationStartedTimestamp = new Date().getTime();
this.compilationPromise = new Promise((resolve, reject) => {
const extractedAssets = [];
Expand Down

0 comments on commit 73d2a66

Please sign in to comment.