google / strict-csp

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Incorrect Hash in webpack production build when filenames uses [contenthash]

todda00 opened this issue · comments

Hello,

We are looking to use the webpack plugin to wrap our SPA in a hashed inline script, and have it working locally, but when the webpack builds in production, the hash that is being generated is incorrect. I have narrowed down the issue to using a webpack config with a filename containing [contenthash]. This fails in a fresh, ejected create-react-app as well when building in production mode.

Reproduction Repo:

https://github.com/todda00/test-csp

Steps to Reproduce:

Clone reproduction repo
Navigate to repo root directory

Run the following:

npm install
npm run build
npx serve -s build

When the output.filename webpack config is changed to something static, the script is hashed correctly. Support for [contenthash] is common and required in many CDN served static production sites such as ours.

Hi @todda00,
Thanks for trying out our experimental plugin, and for taking the time to file this and create a repro repo!
That's definitely a common use case that we'd want to support.
We'll look into this, though most likely not before the next week or two.
We'll post here as soon as we have an update.

I found this additional piece of information about the hashes changing after html-webpack-plugin has emitted the HTML which is what this plugin hashes:

jantimon/html-webpack-plugin#1700

I applied the following to strict-csp-html-webpack-plugin

        compilation.hooks.processAssets.intercept({
          register: (tap) => {
            if (tap.name === 'HtmlWebpackPlugin') {
              tap.stage = webpack.Compilation.PROCESS_ASSETS_STAGE_REPORT;
            }
            return tap;
          },
        })

which did cause the plugin to hash the script correctly. However I have no idea the implications of changing the stage that html-webpack-plugin emits the HTML. I imagine this could cause issues with its interactions with other settings or plugins.

See also: jantimon/html-webpack-plugin#1638

commented

Here's the above fix wrapped in a plugin so it's independent of strict-csp:

import webpack from 'webpack'

export default class ApplyHTMLWebpackPluginHashFixPlugin {
    apply(compiler: webpack.Compiler): void {
        compiler.hooks.compilation.tap(
            'ApplyHTMLWebpackPluginHashFixPlugin',
            (compilation: webpack.Compilation): void => {
                compilation.hooks.processAssets.intercept({
                    register(tap) {
                        if (tap.name === 'HtmlWebpackPlugin') {
                            tap.stage =
                                webpack.Compilation.PROCESS_ASSETS_STAGE_REPORT
                        }
                        return tap
                    },
                })
            },
        )
    }
}