From 07f83682bb53711e94dfce671ff56045e3cb74bd Mon Sep 17 00:00:00 2001 From: Sam Gammon Date: Sat, 15 Oct 2022 19:41:59 -0700 Subject: [PATCH] feat(plugin-webpack): customizable `HtmlWebpackPlugin` options This changeset adds options to entrypoints to support customized operation of the `HtmlWebpackPlugin`. See below for full changeset. Changes enclosed: - Add properties for `output`, `htmlPlugins`, and `htmlOptions` to `WebpackPluginEntryPoint` - Use new options from `Config.ts`, by merging them into their expected places - Add tests to cover new options Fixes and closes electron-userland/electron-forge#2968. --- packages/plugin/webpack/src/Config.ts | 17 +++++++++- packages/plugin/webpack/src/WebpackConfig.ts | 3 ++ .../plugin/webpack/test/WebpackConfig_spec.ts | 31 +++++++++++++++++++ 3 files changed, 50 insertions(+), 1 deletion(-) diff --git a/packages/plugin/webpack/src/Config.ts b/packages/plugin/webpack/src/Config.ts index f0621176fc..73604982ac 100644 --- a/packages/plugin/webpack/src/Config.ts +++ b/packages/plugin/webpack/src/Config.ts @@ -1,6 +1,7 @@ -import { Configuration as RawWebpackConfiguration } from 'webpack'; +import { Configuration as RawWebpackConfiguration, WebpackPluginInstance } from 'webpack'; import WebpackDevServer from 'webpack-dev-server'; import { ConfigurationFactory as WebpackConfigurationFactory } from './WebpackConfig'; +import HtmlWebpackPlugin from 'html-webpack-plugin'; export interface WebpackPluginEntryPoint { /** @@ -48,6 +49,20 @@ export interface WebpackPluginEntryPoint { * for all entries. */ nodeIntegration?: boolean; + /** + * Custom options to merge into the configuration passed to `HtmlWebpackPlugin`. + */ + htmlOptions?: Partial; + /** + * Plugins to include before `HtmlWebpackPlugin`; typically, HTML plugin add-ons will + * need to be placed here. + */ + htmlPlugins?: WebpackPluginInstance[]; + /** + * Additional options to merge into the Webpack `output` configuration for this entry- + * point. + */ + output?: object; } export interface WebpackPreloadEntryPoint { diff --git a/packages/plugin/webpack/src/WebpackConfig.ts b/packages/plugin/webpack/src/WebpackConfig.ts index af481b11b0..bbe888c733 100644 --- a/packages/plugin/webpack/src/WebpackConfig.ts +++ b/packages/plugin/webpack/src/WebpackConfig.ts @@ -195,6 +195,7 @@ export default class WebpackConfigGenerator { devtool: this.rendererSourceMapOption, mode: this.mode, output: { + ...(entryPoint.output || {}), path: path.resolve(this.webpackDir, 'renderer'), filename: '[name]/index.js', globalObject: 'self', @@ -205,9 +206,11 @@ export default class WebpackConfigGenerator { __filename: false, }, plugins: [ + ...(entryPoint.htmlPlugins || []), ...(entryPoint.html ? [ new HtmlWebpackPlugin({ + ...(entryPoint.htmlOptions || {}), title: entryPoint.name, template: entryPoint.html, filename: `${entryPoint.name}/index.html`, diff --git a/packages/plugin/webpack/test/WebpackConfig_spec.ts b/packages/plugin/webpack/test/WebpackConfig_spec.ts index 95b9ce60fa..4c04dc12d0 100644 --- a/packages/plugin/webpack/test/WebpackConfig_spec.ts +++ b/packages/plugin/webpack/test/WebpackConfig_spec.ts @@ -643,6 +643,37 @@ describe('WebpackConfigGenerator', () => { await generator.getRendererConfig(config.renderer.entryPoints); expect(getInvokedCounter()).to.equal(2); }); + + it('honors custom entrypoint output options', async () => { + const { MyWebpackConfigGenerator } = makeSubclass(); + + const config = { + mainConfig: () => ({ + entry: 'main.js', + ...sampleWebpackConfig, + }), + renderer: { + config: { ...sampleWebpackConfig }, + entryPoints: [ + { + name: 'main', + js: 'rendererScript.js', + output: { + crossorigin: 'anonymous', + }, + }, + ], + }, + } as WebpackPluginConfig; + + const generator = new MyWebpackConfigGenerator(config, mockProjectDir, false, 3000); + + const rendererConfig = await generator.getRendererConfig(config.renderer.entryPoints); + // eslint-disable-next-line @typescript-eslint/no-explicit-any + const outputSettings = rendererConfig[0].output as any; + expect(outputSettings).not.to.be.undefined; + expect(outputSettings['crossorigin']).to.equal('anonymous'); + }); }); }); });