webpack 5.1.2 → 5.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of webpack might be problematic. Click here for more details.

Files changed (42) hide show
  1. package/lib/ChunkGraph.js +19 -0
  2. package/lib/Compilation.js +37 -9
  3. package/lib/Compiler.js +26 -2
  4. package/lib/ConditionalInitFragment.js +109 -0
  5. package/lib/ContextModule.js +1 -1
  6. package/lib/DelegatedModule.js +1 -1
  7. package/lib/Dependency.js +1 -0
  8. package/lib/ExportsInfo.js +62 -16
  9. package/lib/ExternalModule.js +7 -6
  10. package/lib/FlagDependencyUsagePlugin.js +38 -42
  11. package/lib/Module.js +8 -0
  12. package/lib/NormalModule.js +26 -20
  13. package/lib/RawModule.js +1 -1
  14. package/lib/RuntimeGlobals.js +5 -0
  15. package/lib/RuntimeModule.js +4 -1
  16. package/lib/RuntimePlugin.js +8 -0
  17. package/lib/RuntimeTemplate.js +41 -0
  18. package/lib/SourceMapDevToolModuleOptionsPlugin.js +25 -0
  19. package/lib/SourceMapDevToolPlugin.js +6 -2
  20. package/lib/Template.js +1 -0
  21. package/lib/WebpackOptionsApply.js +3 -1
  22. package/lib/asset/AssetGenerator.js +10 -6
  23. package/lib/buildChunkGraph.js +111 -25
  24. package/lib/config/browserslistTargetHandler.js +4 -2
  25. package/lib/config/defaults.js +1 -1
  26. package/lib/container/ContainerEntryModule.js +4 -2
  27. package/lib/dependencies/HarmonyAcceptDependency.js +33 -5
  28. package/lib/dependencies/HarmonyImportDependency.js +70 -28
  29. package/lib/dependencies/HarmonyImportSpecifierDependency.js +2 -2
  30. package/lib/dependencies/PureExpressionDependency.js +30 -6
  31. package/lib/dependencies/WorkerPlugin.js +8 -3
  32. package/lib/javascript/JavascriptModulesPlugin.js +16 -10
  33. package/lib/optimize/ConcatenatedModule.js +87 -20
  34. package/lib/optimize/ModuleConcatenationPlugin.js +71 -6
  35. package/lib/optimize/SideEffectsFlagPlugin.js +112 -100
  36. package/lib/runtime/RuntimeIdRuntimeModule.js +29 -0
  37. package/lib/stats/DefaultStatsPrinterPlugin.js +17 -1
  38. package/lib/util/compileBooleanMatcher.js +13 -1
  39. package/lib/util/runtime.js +63 -1
  40. package/package.json +7 -7
  41. package/schemas/WebpackOptions.json +13 -2
  42. package/types.d.ts +63 -8
@@ -5,7 +5,7 @@
5
5
 
6
6
  "use strict";
7
7
 
8
- const { OriginalSource } = require("webpack-sources");
8
+ const { OriginalSource, RawSource } = require("webpack-sources");
9
9
  const AsyncDependenciesBlock = require("../AsyncDependenciesBlock");
10
10
  const Module = require("../Module");
11
11
  const RuntimeGlobals = require("../RuntimeGlobals");
@@ -233,7 +233,9 @@ class ContainerEntryModule extends Module {
233
233
 
234
234
  sources.set(
235
235
  "javascript",
236
- new OriginalSource(source, "webpack/container-entry")
236
+ this.useSourceMap || this.useSimpleSourceMap
237
+ ? new OriginalSource(source, "webpack/container-entry")
238
+ : new RawSource(source)
237
239
  );
238
240
 
239
241
  return {
@@ -5,6 +5,7 @@
5
5
 
6
6
  "use strict";
7
7
 
8
+ const Template = require("../Template");
8
9
  const makeSerializable = require("../util/makeSerializable");
9
10
  const HarmonyImportDependency = require("./HarmonyImportDependency");
10
11
  const NullDependency = require("./NullDependency");
@@ -62,14 +63,41 @@ HarmonyAcceptDependency.Template = class HarmonyAcceptDependencyTemplate extends
62
63
  */
63
64
  apply(dependency, source, templateContext) {
64
65
  const dep = /** @type {HarmonyAcceptDependency} */ (dependency);
65
- const { module, runtimeTemplate } = templateContext;
66
+ const {
67
+ module,
68
+ runtime,
69
+ runtimeRequirements,
70
+ runtimeTemplate,
71
+ moduleGraph,
72
+ chunkGraph
73
+ } = templateContext;
66
74
  const content = dep.dependencies
67
- .filter(dependency =>
68
- HarmonyImportDependency.Template.isImportEmitted(dependency, module)
69
- )
70
75
  .map(dependency => {
76
+ const referencedModule = moduleGraph.getModule(dependency);
77
+ return {
78
+ dependency,
79
+ runtimeCondition: referencedModule
80
+ ? HarmonyImportDependency.Template.getImportEmittedRuntime(
81
+ module,
82
+ referencedModule
83
+ )
84
+ : false
85
+ };
86
+ })
87
+ .filter(({ runtimeCondition }) => runtimeCondition !== false)
88
+ .map(({ dependency, runtimeCondition }) => {
89
+ const condition = runtimeTemplate.runtimeConditionExpression({
90
+ chunkGraph,
91
+ runtime,
92
+ runtimeCondition,
93
+ runtimeRequirements
94
+ });
71
95
  const s = dependency.getImportStatement(true, templateContext);
72
- return s[0] + s[1];
96
+ const code = s[0] + s[1];
97
+ if (condition !== "true") {
98
+ return `if (${condition}) {\n${Template.indent(code)}\n}\n`;
99
+ }
100
+ return code;
73
101
  })
74
102
  .join("");
75
103
 
@@ -5,11 +5,13 @@
5
5
 
6
6
  "use strict";
7
7
 
8
+ const ConditionalInitFragment = require("../ConditionalInitFragment");
8
9
  const Dependency = require("../Dependency");
9
10
  const HarmonyLinkingError = require("../HarmonyLinkingError");
10
11
  const InitFragment = require("../InitFragment");
11
12
  const Template = require("../Template");
12
13
  const AwaitDependenciesInitFragment = require("../async-modules/AwaitDependenciesInitFragment");
14
+ const { filterRuntime, mergeRuntime } = require("../util/runtime");
13
15
  const ModuleDependency = require("./ModuleDependency");
14
16
 
15
17
  /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */
@@ -199,21 +201,38 @@ class HarmonyImportDependency extends ModuleDependency {
199
201
  * @returns {void}
200
202
  */
201
203
  updateHash(hash, context) {
202
- const { chunkGraph } = context;
204
+ const { chunkGraph, runtime, runtimeTemplate } = context;
203
205
  const { moduleGraph } = chunkGraph;
204
206
  super.updateHash(hash, context);
205
- const importedModule = moduleGraph.getModule(this);
206
- if (importedModule) {
207
- const parentModule = moduleGraph.getParentModule(this);
208
- hash.update(
209
- importedModule.getExportsType(
210
- moduleGraph,
211
- parentModule.buildMeta && parentModule.buildMeta.strictHarmonyModule
212
- )
213
- );
214
- if (moduleGraph.isAsync(importedModule)) hash.update("async");
215
- }
216
207
  hash.update(`${this.sourceOrder}`);
208
+ const connection = moduleGraph.getConnection(this);
209
+ if (connection) {
210
+ const importedModule = connection.module;
211
+ if (importedModule) {
212
+ const parentModule = moduleGraph.getParentModule(this);
213
+ hash.update(
214
+ importedModule.getExportsType(
215
+ moduleGraph,
216
+ parentModule.buildMeta && parentModule.buildMeta.strictHarmonyModule
217
+ )
218
+ );
219
+ if (moduleGraph.isAsync(importedModule)) hash.update("async");
220
+ }
221
+ if (runtimeTemplate) {
222
+ const runtimeRequirements = new Set();
223
+ hash.update(
224
+ runtimeTemplate.runtimeConditionExpression({
225
+ chunkGraph,
226
+ runtimeCondition: filterRuntime(runtime, runtime => {
227
+ return connection.isTargetActive(runtime);
228
+ }),
229
+ runtime,
230
+ runtimeRequirements
231
+ })
232
+ );
233
+ for (const rr of runtimeRequirements) hash.update(rr);
234
+ }
235
+ }
217
236
  }
218
237
 
219
238
  serialize(context) {
@@ -231,6 +250,7 @@ class HarmonyImportDependency extends ModuleDependency {
231
250
 
232
251
  module.exports = HarmonyImportDependency;
233
252
 
253
+ /** @type {WeakMap<Module, WeakMap<Module, RuntimeSpec | boolean>>} */
234
254
  const importEmittedMap = new WeakMap();
235
255
 
236
256
  HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends ModuleDependency.Template {
@@ -265,23 +285,42 @@ HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends
265
285
  : dep.request;
266
286
  const key = `harmony import ${moduleKey}`;
267
287
 
268
- if (module) {
269
- let emittedModules = importEmittedMap.get(dep);
288
+ const runtimeCondition = dep.weak
289
+ ? false
290
+ : connection
291
+ ? filterRuntime(runtime, r => connection.isTargetActive(r))
292
+ : true;
293
+
294
+ if (module && referencedModule) {
295
+ let emittedModules = importEmittedMap.get(module);
270
296
  if (emittedModules === undefined) {
271
- emittedModules = new WeakSet();
272
- importEmittedMap.set(dep, emittedModules);
297
+ emittedModules = new WeakMap();
298
+ importEmittedMap.set(module, emittedModules);
299
+ }
300
+ let mergedRuntimeCondition = runtimeCondition;
301
+ const oldRuntimeCondition = emittedModules.get(referencedModule) || false;
302
+ if (oldRuntimeCondition !== false && mergedRuntimeCondition !== true) {
303
+ if (mergedRuntimeCondition === false || oldRuntimeCondition === true) {
304
+ mergedRuntimeCondition = oldRuntimeCondition;
305
+ } else {
306
+ mergedRuntimeCondition = mergeRuntime(
307
+ oldRuntimeCondition,
308
+ mergedRuntimeCondition
309
+ );
310
+ }
273
311
  }
274
- emittedModules.add(module);
312
+ emittedModules.set(referencedModule, mergedRuntimeCondition);
275
313
  }
276
314
 
277
315
  const importStatement = dep.getImportStatement(false, templateContext);
278
316
  if (templateContext.moduleGraph.isAsync(referencedModule)) {
279
317
  templateContext.initFragments.push(
280
- new InitFragment(
318
+ new ConditionalInitFragment(
281
319
  importStatement[0],
282
320
  InitFragment.STAGE_HARMONY_IMPORTS,
283
321
  dep.sourceOrder,
284
- key
322
+ key,
323
+ runtimeCondition
285
324
  )
286
325
  );
287
326
  templateContext.initFragments.push(
@@ -290,20 +329,22 @@ HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends
290
329
  )
291
330
  );
292
331
  templateContext.initFragments.push(
293
- new InitFragment(
332
+ new ConditionalInitFragment(
294
333
  importStatement[1],
295
334
  InitFragment.STAGE_ASYNC_HARMONY_IMPORTS,
296
335
  dep.sourceOrder,
297
- key + " compat"
336
+ key + " compat",
337
+ runtimeCondition
298
338
  )
299
339
  );
300
340
  } else {
301
341
  templateContext.initFragments.push(
302
- new InitFragment(
342
+ new ConditionalInitFragment(
303
343
  importStatement[0] + importStatement[1],
304
344
  InitFragment.STAGE_HARMONY_IMPORTS,
305
345
  dep.sourceOrder,
306
- key
346
+ key,
347
+ runtimeCondition
307
348
  )
308
349
  );
309
350
  }
@@ -311,12 +352,13 @@ HarmonyImportDependency.Template = class HarmonyImportDependencyTemplate extends
311
352
 
312
353
  /**
313
354
  *
314
- * @param {Dependency} dep the dependency
315
355
  * @param {Module} module the module
316
- * @returns {boolean} true, when for this dependency and module a import init fragment was created
356
+ * @param {Module} referencedModule the referenced module
357
+ * @returns {RuntimeSpec | boolean} runtimeCondition in which this import has been emitted
317
358
  */
318
- static isImportEmitted(dep, module) {
319
- const emittedModules = importEmittedMap.get(dep);
320
- return emittedModules !== undefined && emittedModules.has(module);
359
+ static getImportEmittedRuntime(module, referencedModule) {
360
+ const emittedModules = importEmittedMap.get(module);
361
+ if (emittedModules === undefined) return false;
362
+ return emittedModules.get(referencedModule) || false;
321
363
  }
322
364
  };
@@ -196,7 +196,7 @@ class HarmonyImportSpecifierDependency extends HarmonyImportDependency {
196
196
  * @returns {void}
197
197
  */
198
198
  updateHash(hash, context) {
199
- const { chunkGraph } = context;
199
+ const { chunkGraph, runtime } = context;
200
200
  super.updateHash(hash, context);
201
201
  const moduleGraph = chunkGraph.moduleGraph;
202
202
  const importedModule = moduleGraph.getModule(this);
@@ -204,7 +204,7 @@ class HarmonyImportSpecifierDependency extends HarmonyImportDependency {
204
204
  hash.update(ids.join());
205
205
  if (importedModule) {
206
206
  const exportsInfo = moduleGraph.getExportsInfo(importedModule);
207
- hash.update(`${exportsInfo.getUsedName(ids, context.runtime)}`);
207
+ hash.update(`${exportsInfo.getUsedName(ids, runtime)}`);
208
208
  }
209
209
  }
210
210
 
@@ -7,6 +7,7 @@
7
7
 
8
8
  const { UsageState } = require("../ExportsInfo");
9
9
  const makeSerializable = require("../util/makeSerializable");
10
+ const { filterRuntime } = require("../util/runtime");
10
11
  const NullDependency = require("./NullDependency");
11
12
 
12
13
  /** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */
@@ -74,22 +75,45 @@ PureExpressionDependency.Template = class PureExpressionDependencyTemplate exten
74
75
  * @param {DependencyTemplateContext} templateContext the context object
75
76
  * @returns {void}
76
77
  */
77
- apply(dependency, source, { moduleGraph, runtime }) {
78
+ apply(
79
+ dependency,
80
+ source,
81
+ { chunkGraph, moduleGraph, runtime, runtimeTemplate, runtimeRequirements }
82
+ ) {
78
83
  const dep = /** @type {PureExpressionDependency} */ (dependency);
79
84
 
80
- if (dep.usedByExports !== false) {
85
+ const usedByExports = dep.usedByExports;
86
+ if (usedByExports !== false) {
81
87
  const selfModule = moduleGraph.getParentModule(dep);
82
88
  const exportsInfo = moduleGraph.getExportsInfo(selfModule);
83
- for (const exportName of dep.usedByExports) {
84
- if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) {
85
- return;
89
+ const runtimeCondition = filterRuntime(runtime, runtime => {
90
+ for (const exportName of usedByExports) {
91
+ if (exportsInfo.getUsed(exportName, runtime) !== UsageState.Unused) {
92
+ return true;
93
+ }
86
94
  }
95
+ return false;
96
+ });
97
+ if (runtimeCondition === true) return;
98
+ if (runtimeCondition !== false) {
99
+ const condition = runtimeTemplate.runtimeConditionExpression({
100
+ chunkGraph,
101
+ runtime,
102
+ runtimeCondition,
103
+ runtimeRequirements
104
+ });
105
+ source.insert(
106
+ dep.range[0],
107
+ `(/* runtime-dependent pure expression or super */ ${condition} ? (`
108
+ );
109
+ source.insert(dep.range[1], ") : null)");
110
+ return;
87
111
  }
88
112
  }
89
113
 
90
114
  source.insert(
91
115
  dep.range[0],
92
- "(/* unused pure expression or super */ null && ("
116
+ `(/* unused pure expression or super */ null && (`
93
117
  );
94
118
  source.insert(dep.range[1], "))");
95
119
  }
@@ -12,6 +12,7 @@ const UnsupportedFeatureWarning = require("../UnsupportedFeatureWarning");
12
12
  const formatLocation = require("../formatLocation");
13
13
  const EnableChunkLoadingPlugin = require("../javascript/EnableChunkLoadingPlugin");
14
14
  const { equals } = require("../util/ArrayHelpers");
15
+ const { contextify } = require("../util/identifier");
15
16
  const {
16
17
  harmonySpecifierTag
17
18
  } = require("./HarmonyImportDependencyParserPlugin");
@@ -48,6 +49,10 @@ class WorkerPlugin {
48
49
  if (this._chunkLoading) {
49
50
  new EnableChunkLoadingPlugin(this._chunkLoading).apply(compiler);
50
51
  }
52
+ const cachedContextify = contextify.bindContextCache(
53
+ compiler.context,
54
+ compiler.root
55
+ );
51
56
  compiler.hooks.thisCompilation.tap(
52
57
  "WorkerPlugin",
53
58
  (compilation, { normalModuleFactory }) => {
@@ -213,9 +218,9 @@ class WorkerPlugin {
213
218
  }
214
219
 
215
220
  if (!entryOptions.runtime) {
216
- entryOptions.runtime = `${parser.state.module.identifier()}|${formatLocation(
217
- expr.loc
218
- )}`;
221
+ entryOptions.runtime = `${cachedContextify(
222
+ parser.state.module.identifier()
223
+ )}|${formatLocation(expr.loc)}`;
219
224
  }
220
225
 
221
226
  const block = new AsyncDependenciesBlock({
@@ -5,7 +5,7 @@
5
5
 
6
6
  "use strict";
7
7
 
8
- const { SyncWaterfallHook, SyncHook } = require("tapable");
8
+ const { SyncWaterfallHook, SyncHook, SyncBailHook } = require("tapable");
9
9
  const {
10
10
  ConcatSource,
11
11
  OriginalSource,
@@ -103,6 +103,7 @@ const chunkHasJs = (chunk, chunkGraph) => {
103
103
  * @property {SyncWaterfallHook<[Source, RenderContext]>} render
104
104
  * @property {SyncWaterfallHook<[string, RenderBootstrapContext]>} renderRequire
105
105
  * @property {SyncHook<[Chunk, Hash, ChunkHashContext]>} chunkHash
106
+ * @property {SyncBailHook<[Chunk, RenderContext], boolean>} useSourceMap
106
107
  */
107
108
 
108
109
  /** @type {WeakMap<Compilation, CompilationHooks>} */
@@ -141,7 +142,8 @@ class JavascriptModulesPlugin {
141
142
  renderChunk: new SyncWaterfallHook(["source", "renderContext"]),
142
143
  renderMain: new SyncWaterfallHook(["source", "renderContext"]),
143
144
  renderRequire: new SyncWaterfallHook(["code", "renderContext"]),
144
- chunkHash: new SyncHook(["chunk", "hash", "context"])
145
+ chunkHash: new SyncHook(["chunk", "hash", "context"]),
146
+ useSourceMap: new SyncBailHook(["chunk", "renderContext"])
145
147
  };
146
148
  compilationHooksMap.set(compilation, hooks);
147
149
  }
@@ -272,6 +274,9 @@ class JavascriptModulesPlugin {
272
274
  chunk,
273
275
  contentHashType: "javascript"
274
276
  },
277
+ info: {
278
+ javascriptModule: compilation.runtimeTemplate.isModule()
279
+ },
275
280
  identifier: hotUpdateChunk
276
281
  ? `hotupdatechunk${chunk.id}`
277
282
  : `chunk${chunk.id}`,
@@ -531,6 +536,7 @@ class JavascriptModulesPlugin {
531
536
  const iife = runtimeTemplate.isIIFE();
532
537
 
533
538
  const bootstrap = this.renderBootstrap(renderContext, hooks);
539
+ const useSourceMap = hooks.useSourceMap.call(chunk, renderContext);
534
540
 
535
541
  const allModules = Array.from(
536
542
  chunkGraph.getOrderedChunkModulesIterableBySourceType(
@@ -590,13 +596,13 @@ class JavascriptModulesPlugin {
590
596
  }
591
597
 
592
598
  if (bootstrap.header.length > 0) {
599
+ const header = Template.asString(bootstrap.header) + "\n";
593
600
  source.add(
594
601
  new PrefixSource(
595
602
  prefix,
596
- new OriginalSource(
597
- Template.asString(bootstrap.header) + "\n",
598
- "webpack/bootstrap"
599
- )
603
+ useSourceMap
604
+ ? new OriginalSource(header, "webpack/bootstrap")
605
+ : new RawSource(header)
600
606
  )
601
607
  );
602
608
  source.add(
@@ -653,13 +659,13 @@ class JavascriptModulesPlugin {
653
659
  }
654
660
  }
655
661
  } else {
662
+ const startup = Template.asString(bootstrap.startup) + "\n";
656
663
  source.add(
657
664
  new PrefixSource(
658
665
  prefix,
659
- new OriginalSource(
660
- Template.asString(bootstrap.startup) + "\n",
661
- "webpack/startup"
662
- )
666
+ useSourceMap
667
+ ? new OriginalSource(startup, "webpack/startup")
668
+ : new RawSource(startup)
663
669
  )
664
670
  );
665
671
  }