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

Memory leak from child compilation in watch mode (Sources strings) #17857

Closed
helloitsjoe opened this issue Dec 11, 2023 · 5 comments
Closed

Memory leak from child compilation in watch mode (Sources strings) #17857

helloitsjoe opened this issue Dec 11, 2023 · 5 comments

Comments

@helloitsjoe
Copy link
Contributor

helloitsjoe commented Dec 11, 2023

Bug report

NOTE: This issue is very similar to #17851 (child compilations), but these are two separate leaks. This one is related to duplicate strings added to the in-memory cache.

What is the current behavior?

When running in watch mode, Webpack caches source code from child compilations (e.g. HtmlWebpackPlugin) without removing them:

Duplicated strings in memory Duplicate strings
Retained Sources Retained Sources

The leak is worse when we have build-time dependencies, as in the reproduction repo:

Duplicated build-time dependencies source strings

Investigation done

One place these are being cached is in a Map in MemoryCachePlugin. When a child compiler caches them it uses the child compiler ID, for example (note the HtmlWebpackPlugin_0-7, the 7th time I ran a recompilation):

'HtmlWebpackCompiler|0|Compilation/codeGeneration|javascript/esm|data:text/javascript,__webpack_public_path__ = __webpack_base_uri__ = htmlWebpackPluginPublicPath;|HtmlWebpackPlugin_0-7'

This seems problematic because entry will never be found, since the key uses an ID unique to each iteration.

If the current behavior is a bug, please provide the steps to reproduce.

Minimal reproduction repo including steps to reproduce here: https://github.com/helloitsjoe/webpack-cache-memory-leak

What is the expected behavior?

Dependency source code should be cached only once (or maybe twice including the child compilation). A few potential options:

  1. Remove the child compiler sources from the cache during _cleanupLastCompilation, but I don't see a way to clear entries from the MemoryCache map currently.
  2. Only cache compiler sources for the parent compilation, or replace the previous child compilation's cached sources.

I'm also not sure MemoryCache is the only place the sources are being referenced, so fixing this leak might require more changes. I'm happy to help however I can.

Other relevant information:
webpack version: 5.89.0
Node.js version: 20.5.1
Operating System: MacOS (darwin 22.5.0)
Additional tools: HtmlWebpackPlugin (child compiler), custom loader in https://github.com/helloitsjoe/webpack-cache-memory-leak to cache build-time dependency sources

@helloitsjoe helloitsjoe changed the title Sources memory leak from child compilation in watch mode Memory leak from child compilation in watch mode (Sources strings) Dec 11, 2023
@alexander-akait
Copy link
Member

Thank you for the issue, do you want send a PR with fix?

@helloitsjoe
Copy link
Contributor Author

helloitsjoe commented Dec 12, 2023

I will see if I can determine the root cause here, it's not clear to me yet. This might actually be an issue in HtmlWebpackPlugin, if that turns out to be the source I'll close this issue!

@helloitsjoe
Copy link
Contributor Author

I think I've narrowed this down to a commit in HtmlWebpackPlugin. I've opened an issue over there, I'll follow up here if it's confirmed to be a problem there: jantimon/html-webpack-plugin#1835

@helloitsjoe
Copy link
Contributor Author

@alexander-akait I noticed you're a maintainer of HtmlWebpackPlugin as well, does the change I'm suggesting in this PR look like a reasonable fix for this? jantimon/html-webpack-plugin#1836

I'm happy to look more into this if not.

@helloitsjoe
Copy link
Contributor Author

Thank you!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants