threads-plugin
threads-plugin copied to clipboard
HMR breaks on changes unless "name" is specified in Worker constructor
Without "name" specified as a second argument to the Worker
constructor, Webpack HMR compilation fails whenever the worker file changes:
Initial compile at startup:
Entrypoint main = main.dev.js
[./index.js] 2.93 KiB {main} [built]
+ 2021 hidden modules
Child WorkerPluginLoader:
Asset Size Chunks Chunk Names
0.main.dev.worker.js 131 KiB 0 [emitted]
Entrypoint undefined = 0.main.dev.worker.js
On change:
ERROR in ./my.worker.js (./node_modules/threads-plugin/dist/loader.js!./my.worker.js)
Module build failed (from ./node_modules/threads-plugin/dist/loader.js):
Error: WorkerPlugin: no entry for /app/node_modules/babel-loader/lib/index.js??ref--4-0!/app/my.worker.js
at /app/node_modules/threads-plugin/src/loader.js:84:16
Child WorkerPluginLoader:
Asset Size Chunks Chunk Names
341686a42eabf014d90f.hot-update.json 44 bytes
Entrypoint undefined =
When "name" is specified, it's used as the entrypoint name and the compilation succeeds, e.g.
new Worker('./my.worker', { name: 'myworker' });
It might also be worth noting that changing the name while the dev server is running also breaks HMR.
While documenting this would be good, I wonder if an entrypoint name could be generated instead.
Hey @barretron!
I am terribly sorry, I just saw your issue. For some reason I wasn't automatically watching the repository...
Is that still an issue or did you give up on it by now?
No worries! It's still an issue, but I was able to work around it once I figured out what was going on by using the name
field in the second argument to Worker
. It would be great, though, to be able to use new Worker('path')
and have the plugin generate a default name if none is specified (the plugin seems to do that anyway with the output filename).
I just ported the latest changes of GoogleChromeLabs/worker-plugin
and published it as threads-plugin
v1.1.0
. Would be great if you can give it a try - I think it should be fixed now 🙂
@andywer the changes prevented that app from crashing, but unfortunately the chunk name seems to be incremented each reload, resulting in an accumulation of new workers each time. The chunk name needs to remain the same through each reload so that webpack knows which module to replace.
I just saw that there is a subtle difference to the latest version of the worker-plugin
: The place where the worker ID counter is declared.
Can you quickly try monkey-patching your local node_modules/threads-plugin/dist/threads-plugin.js
?
@barretron
WorkerPlugin.prototype.apply = function apply (compiler) {
var workerId = 0;
compiler.hooks.normalModuleFactory.tap(NAME, function (factory) {
+ workerId = 0;
for (var i = 0, list = JS_TYPES; i < list.length; i += 1) {
That change kept the filename the same, but introduced new warnings.
It looks like some of what's happening can be fixed on my end (with the numbered workers piling up) by adding code to terminate the thread pool on change.
if (module.hot) {
module.hot.dispose(async () => {
await pool.terminate(true);
await pool.completed(true);
});
}
So that might not be an issue.
When I did the monkey-patch (and restarted the dev server, etc.), I saw the following output on the console:
ℹ 「wdm」: Compiling...
âš ï½¢wdmï½£: Hash: 5c8d20e526764d845570
Version: webpack 4.39.3
Time: 6978ms
Built at: 09/13/2019 9:24:22 AM
Asset Size Chunks Chunk Names
0.e98ba9dac624b1cf4d6e.hot-update.js 35.7 KiB [emitted]
0.renderer.dev.js 6.08 KiB 0
0.renderer.dev.worker.js 2.67 MiB [emitted]
0d11544364bc4541af96267ca8b2a5ce.woff2 21.5 KiB
21955254e41869cea3f5a1769ab1cbe6.woff 28.3 KiB
239cf85916292b3585d17ba1f7801dbb.woff2 20.5 KiB
29b164482600fc3976b5b2c863d69b71.woff 27.6 KiB
3c9d154e1fa888849c63a616e2f09b3c.woff2 22.2 KiB
448c34a56d699c29117adc64c43affeb.woff2 17.6 KiB
44913051ee3d4536cd4fa368067e9a83.woff 26.5 KiB
4a8c46be9056c47cc8d0e3a3a70ae193.woff 28.6 KiB
4ff19ede4cf2a2a07c638795a389f6df.woff2 22.9 KiB
5b173e43e6e846589858d97fa0b406c9.woff 27.5 KiB
63c5b6176f60881d53dd2dc10904a04c.woff2 22.1 KiB
674f50d287a8c48dc19ba404d20fe713.eot 162 KiB
73ce1e5f9e44d490f48490673038d5d3.woff 25.2 KiB
7bbbfedc5560813c2e0d20966360dfdf.ttf 248 KiB
80a9477d95ed5ca6e64843c1024e9e7f.woff 26.9 KiB
89889688147bd7575d6327160d64e760.svg 106 KiB
912ec66d7572ff821749319396470bde.svg 434 KiB
9578c8a599ff9b3b328f306da81607f0.woff2 21.6 KiB
9ac1b95369577a48fdf2.hot-update.json 35 bytes [emitted]
9ac3d9de00cce6d3352a889816226451.woff2 22.6 KiB
9c1d6e0e66641c7c0806a5ad1b3d9286.woff2 23.3 KiB
a7db29488272756e766b024e6aebe848.woff2 22.6 KiB
af7ae505a9eed503f8b8e6982036873e.woff2 75.4 KiB
b06871f281fee6b241d60582ae9369b9.ttf 162 KiB
b7a94712079cba234be3f546cf42f588.woff 26.6 KiB
bec9243368f86e688b23bc1852823d0b.woff 27.6 KiB
c2356fc49835b1870dcc5b07799b4920.ttf 333 KiB
d8de1d9a8a017aed7e74649e8e06eeb5.woff2 23.2 KiB
e18bbf611f2a2e43afc071aa2f4e1512.ttf 44.3 KiB
e98ba9dac624b1cf4d6e.hot-update.json 43 bytes [emitted]
ebc68b684a448cc84dd1744d01e14340.ttf 246 KiB
ee45bcafa9fa4ac621e7ce2de5f931db.ttf 324 KiB
f4769f9bdb7466be65088239c12046d1.eot 19.7 KiB
f778b3151e4b3ed5b831e9e8646ab207.woff 28 KiB
fa2772327f55d8198301fdb8bcfc8158.woff 22.9 KiB
fee66e712a8a08eef5805a46892932ad.woff 95.7 KiB
renderer.dev.js 22.5 MiB main [emitted] main
Entrypoint main = renderer.dev.js
[0] multi (webpack)-dev-server/client?http://localhost:1212 (webpack)/hot/dev-server.js react-hot-loader/patch webpack-dev-server/client?http://localhost:1212 webpack/hot/only-dev-server ./app/index.js 88 bytes {main}
[./app/app.global.scss] 1.64 KiB {main}
[./app/containers/Root.js] 2.01 KiB {main}
[./app/index.js] 4.32 KiB {main}
[./app/sagas/index.js] 2.67 KiB {main}
[./app/store/configureStore.js] 350 bytes {main}
[./app/store/fs/settings.js] 3.19 KiB {main}
[./app/store/graphql/client.js] 1.01 KiB {main}
[./node_modules/blocked-at/index.js] 2.01 KiB {0}
[./node_modules/moment-timezone/index.js] 114 bytes {main}
[./node_modules/react-dom/index.js] 1.33 KiB {main}
[./node_modules/react-hot-loader/patch.js] 229 bytes {main}
[./node_modules/webpack-dev-server/client/index.js?http://localhost:1212] (webpack)-dev-server/client?http://localhost:1212 4.29 KiB {main}
[./node_modules/webpack/hot/dev-server.js] (webpack)/hot/dev-server.js 1.59 KiB {main}
[./node_modules/webpack/hot/only-dev-server.js] (webpack)/hot/only-dev-server.js 2.52 KiB {main}
+ 2109 hidden modules
WARNING in No instantiations of threads.js workers found.
Please check that:
1. You have configured Babel / TypeScript to not transpile ES modules
2. You import `Worker` from `threads` where you use it
For more details see: https://github.com/andywer/threads-plugin
Child WorkerPluginLoader:
Asset Size Chunks Chunk Names
0.e98ba9dac624b1cf4d6e.hot-update.js 35.7 KiB 0 [emitted] 0
0.renderer.dev.worker.js 2.67 MiB 0 [emitted] 0
e98ba9dac624b1cf4d6e.hot-update.json 43 bytes [emitted]
Entrypoint 0 = 0.renderer.dev.worker.js 0.e98ba9dac624b1cf4d6e.hot-update.js
[./node_modules/babel-loader/lib/index.js?!./app/utils/perforce/my.worker.js] ./node_modules/babel-loader/lib??ref--4-0!./app/utils/perforce/my.worker.js 12.7 KiB {0} [built]
[./node_modules/fast-levenshtein/levenshtein.js] 3.84 KiB {0}
[./node_modules/hoist-non-react-statics/dist/hoist-non-react-statics.cjs.js] 2.82 KiB {0}
[./node_modules/is-observable/index.js] 186 bytes {0}
[./node_modules/prop-types/index.js] 710 bytes {0}
[./node_modules/react-dom/index.js] 1.33 KiB {0}
[./node_modules/react-hot-loader/dist/react-hot-loader.development.js] 90.2 KiB {0}
[./node_modules/react-hot-loader/dist/react-hot-loader.production.min.js] 1.08 KiB {0}
[./node_modules/react-hot-loader/index.js] 1.24 KiB {0}
[./node_modules/react-lifecycles-compat/react-lifecycles-compat.es.js] 5.91 KiB {0}
[./node_modules/react/index.js] 190 bytes {0}
[./node_modules/shallowequal/index.js] 979 bytes {0}
[./node_modules/threads/dist/worker/index.js] 7.11 KiB {0}
[./node_modules/threads/worker.js] 48 bytes {0}
[./node_modules/webpack/buildin/harmony-module.js] (webpack)/buildin/harmony-module.js 573 bytes {0}
+ 22 hidden modules
WARNING in No instantiations of threads.js workers found.
Please check that:
1. You have configured Babel / TypeScript to not transpile ES modules
2. You import `Worker` from `threads` where you use it
For more details see: https://github.com/andywer/threads-plugin
ℹ 「wdm」: Compiled with warnings.
And in the Chrome debugger...
Note: the rest of this info is unrelated to the original issue, but the solution to the original issue might be related to the following:
I should also note that, regardless of method (named Worker, release version, and patched version), HMR does not update the Worker module at all. Webpack will compile the new file, but does not reload the module, instead showing this message:
Since the output chunk is a new entry point with no exports, I'm wondering if there's something that needs to be implemented on the plugin end to make Webpack aware of the module's position in the dependency tree. I tried manually module.hot.accept
ing dependent Workers in the parent module, but that still didn't trigger a module update.