Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Not compatible with Webpack's splitChunks.cacheGroups config #36

Closed
mlmmn opened this issue Jan 13, 2024 · 2 comments · Fixed by #38
Closed

Not compatible with Webpack's splitChunks.cacheGroups config #36

mlmmn opened this issue Jan 13, 2024 · 2 comments · Fixed by #38

Comments

@mlmmn
Copy link
Contributor

mlmmn commented Jan 13, 2024

hydration-overlay-initializer.js relies on presence of react-dom string in event filename, namely const isReactDomError = event.filename.includes("react-dom");. This won't work when chunk that contains ReactDOM lib is renamed. Below is an extract from a real world Webpack config:

const vendorNames = [
    'react',
    'react-dom',
    'react-router-dom',
    'react-router',
    'react-helmet-async'
];

const webpackConfig = {
    optimization: {
        splitChunks: {
            chunks: 'all',
            cacheGroups: {
                vendor: {
                    test: new RegExp(
                        `[\\/]node_modules[\\/](${vendorNames.join('|')})[\\/]`
                    ),
                    name: 'vendor',
                    chunks: 'all',
                    enforce: true
                }
            }
        }
    }
};

This config puts listed dependencies inside vendor.chunk.js module which obviously does not satisfy aforementioned condition. To mitigate this issue within workbase that I'm working on, I copied the contents of hydration-overlay-initializer.js script and modified it like so:

const HYDRATION_ERROR_REGEX_LIST = [
    /^Uncaught Error: Hydration failed/,
    /^Uncaught Error: There was an error while hydrating/
];

window.BUILDER_HYDRATION_OVERLAY = {};
window.addEventListener('error', event => {
    // Removed `react-dom` condition entirely
    const isHydrationMsg = HYDRATION_ERROR_REGEX_LIST.some(regexp => regexp.test(event.message));

    if (isHydrationMsg) {
        window.BUILDER_HYDRATION_OVERLAY.ERROR = true;
        const appRootEl = document.querySelector('#hydrate-root');
        if (appRootEl) {
            window.BUILDER_HYDRATION_OVERLAY.CSR_HTML = appRootEl.innerHTML;
        }
    }
});
const BUILDER_HYDRATION_OVERLAY_ELEMENT = document.querySelector('#hydrate-root');
if (BUILDER_HYDRATION_OVERLAY_ELEMENT) {
    window.BUILDER_HYDRATION_OVERLAY.SSR_HTML = BUILDER_HYDRATION_OVERLAY_ELEMENT.innerHTML;
}

Then this module is simply imported within bootstrap code. I believe this is not an ideal solution, but I hope it helps to shed some light on the issue as well as iterating to find a decent solution ✌️

@samijaber
Copy link
Contributor

You're right. I think we can get away with removing the filename check completely. Any error message with "hydration" or "hydrating" should be good enough of a condition IMO. Would you be interested in putting up a PR? Should be a one-liner 😃

@mlmmn
Copy link
Contributor Author

mlmmn commented Jan 21, 2024

@samijaber just opened a PR ✌️

samijaber added a commit that referenced this issue Jan 22, 2024
Fixes #36

---------

Co-authored-by: Miłosław Politowski <miloslaw.politowski@olx.pl>
Co-authored-by: Sami Jaber <me@sami.website>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants