webpack 5.108.3 → 5.109.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.
- package/lib/APIPlugin.js +48 -29
- package/lib/CacheFacade.js +8 -0
- package/lib/ChunkGroup.js +1 -0
- package/lib/CompatibilityPlugin.js +31 -29
- package/lib/Compilation.js +50 -8
- package/lib/ConstPlugin.js +11 -11
- package/lib/ContextModule.js +239 -6
- package/lib/ContextModuleFactory.js +139 -14
- package/lib/DefinePlugin.js +396 -101
- package/lib/Entrypoint.js +1 -1
- package/lib/ExportsInfoApiPlugin.js +2 -2
- package/lib/ExternalModule.js +107 -5
- package/lib/ExternalModuleFactoryPlugin.js +20 -1
- package/lib/FileSystemInfo.js +130 -74
- package/lib/FlagDependencyExportsPlugin.js +55 -8
- package/lib/HotModuleReplacementPlugin.js +18 -15
- package/lib/LazyBarrel.js +30 -3
- package/lib/Module.js +3 -0
- package/lib/ModuleFilenameHelpers.js +2 -2
- package/lib/ModuleTypeConstants.js +8 -1
- package/lib/MultiCompiler.js +13 -2
- package/lib/MultiWatching.js +1 -0
- package/lib/NodeStuffPlugin.js +51 -33
- package/lib/NormalModule.js +169 -405
- package/lib/NormalModuleFactory.js +76 -2
- package/lib/ProgressPlugin.js +211 -119
- package/lib/ProvidePlugin.js +2 -2
- package/lib/RuntimeGlobals.js +47 -0
- package/lib/RuntimePlugin.js +33 -0
- package/lib/RuntimeTemplate.js +304 -16
- package/lib/UseStrictPlugin.js +1 -1
- package/lib/WebpackIsIncludedPlugin.js +1 -1
- package/lib/WebpackOptionsApply.js +24 -19
- package/lib/asset/AssetGenerator.js +110 -28
- package/lib/asset/AssetModulesPlugin.js +92 -2
- package/lib/asset/WebManifestGenerator.js +164 -0
- package/lib/asset/WebManifestParser.js +130 -0
- package/lib/async-modules/AwaitDependenciesInitFragment.js +14 -4
- package/lib/async-modules/isGeneratorLowered.js +26 -0
- package/lib/cache/PackFileCacheStrategy.js +9 -3
- package/lib/config/browserslistTargetHandler.js +40 -0
- package/lib/config/defaults.js +222 -32
- package/lib/config/normalization.js +26 -0
- package/lib/config/target.js +9 -1
- package/lib/css/CssGenerator.js +73 -73
- package/lib/css/CssLoadingRuntimeModule.js +5 -1
- package/lib/css/CssModulesPlugin.js +92 -53
- package/lib/css/CssParser.js +843 -302
- package/lib/css/syntax.js +1219 -483
- package/lib/dependencies/AMDDefineDependencyParserPlugin.js +6 -6
- package/lib/dependencies/AMDPlugin.js +2 -2
- package/lib/dependencies/AMDRequireDependenciesBlockParserPlugin.js +13 -13
- package/lib/dependencies/CommonJsDependencyHelpers.js +39 -0
- package/lib/dependencies/CommonJsExportsDependency.js +47 -2
- package/lib/dependencies/CommonJsExportsParserPlugin.js +10 -10
- package/lib/dependencies/CommonJsImportsParserPlugin.js +18 -18
- package/lib/dependencies/CommonJsPlugin.js +2 -2
- package/lib/dependencies/CommonJsRequireDependency.js +26 -1
- package/lib/dependencies/CommonJsSelfReferenceDependency.js +32 -1
- package/lib/dependencies/ContextDependencyHelpers.js +3 -3
- package/lib/dependencies/CreateRequireParserPlugin.js +6 -6
- package/lib/dependencies/CssIcssExportDependency.js +190 -87
- package/lib/dependencies/CssUrlDependency.js +35 -4
- package/lib/dependencies/ExternalModuleInitFragmentDependency.js +2 -2
- package/lib/dependencies/HarmonyCompatibilityDependency.js +32 -14
- package/lib/dependencies/HarmonyDetectionParserPlugin.js +43 -13
- package/lib/dependencies/HarmonyExportDependencyParserPlugin.js +7 -19
- package/lib/dependencies/HarmonyImportDependency.js +12 -1
- package/lib/dependencies/HarmonyImportDependencyParserPlugin.js +34 -107
- package/lib/dependencies/HarmonyImportGuard.js +192 -20
- package/lib/dependencies/HarmonyModulesPlugin.js +6 -0
- package/lib/dependencies/HarmonyTopLevelThisParserPlugin.js +1 -1
- package/lib/dependencies/HtmlEntryDependency.js +797 -172
- package/lib/dependencies/HtmlSourceDependency.js +26 -0
- package/lib/dependencies/ImportDependency.js +43 -1
- package/lib/dependencies/ImportMetaContextDependencyParserPlugin.js +31 -18
- package/lib/dependencies/ImportMetaContextPlugin.js +38 -7
- package/lib/dependencies/ImportMetaGlobDependency.js +81 -0
- package/lib/dependencies/ImportMetaGlobDependencyParserPlugin.js +78 -0
- package/lib/dependencies/ImportMetaGlobHelpers.js +660 -0
- package/lib/dependencies/ImportMetaPlugin.js +532 -180
- package/lib/dependencies/ImportMetaResolveDependency.js +90 -0
- package/lib/dependencies/ImportParserPlugin.js +87 -26
- package/lib/dependencies/ImportPhase.js +10 -8
- package/lib/dependencies/LoaderPlugin.js +5 -1
- package/lib/dependencies/RequireContextDependencyParserPlugin.js +1 -1
- package/lib/dependencies/RequireEnsureDependenciesBlockParserPlugin.js +3 -6
- package/lib/dependencies/RequireIncludeDependencyParserPlugin.js +4 -11
- package/lib/dependencies/SystemPlugin.js +2 -4
- package/lib/dependencies/TopLevelAwaitDependency.js +93 -0
- package/lib/dependencies/URLDependency.js +141 -21
- package/lib/dependencies/{WorkerPlugin.js → WorkerAndWorkletPlugin.js} +324 -112
- package/lib/dependencies/WorkerDependency.js +86 -18
- package/lib/dependencies/WorkletDependency.js +278 -0
- package/lib/dll/DelegatedModuleFactoryPlugin.js +19 -0
- package/lib/errors/EnvironmentNotSupportAsyncWarning.js +1 -1
- package/lib/errors/LoaderLoadingError.js +20 -0
- package/lib/errors/ModuleParseError.js +39 -22
- package/lib/errors/NodeStuffInWebError.js +1 -1
- package/lib/esm/ModuleChunkFormatPlugin.js +47 -14
- package/lib/esm/ModuleChunkLoadingPlugin.js +8 -1
- package/lib/esm/ModuleChunkLoadingRuntimeModule.js +29 -1
- package/lib/hmr/lazyCompilationBackend.js +32 -8
- package/lib/html/HtmlGenerator.js +940 -91
- package/lib/html/HtmlModule.js +3 -2
- package/lib/html/HtmlModulesPlugin.js +625 -170
- package/lib/html/HtmlParser.js +812 -340
- package/lib/html/favicon.svg +1 -0
- package/lib/html/syntax.js +2116 -834
- package/lib/ids/IdHelpers.js +1 -1
- package/lib/index.js +6 -0
- package/lib/javascript/ArrayPushCallbackChunkFormatPlugin.js +4 -5
- package/lib/javascript/BasicEvaluatedExpression.js +366 -48
- package/lib/javascript/JavascriptGenerator.js +197 -49
- package/lib/javascript/JavascriptModulesPlugin.js +178 -24
- package/lib/javascript/JavascriptParser.js +711 -355
- package/lib/javascript/JavascriptParserHelpers.js +3 -6
- package/lib/javascript/syntax.js +4380 -0
- package/lib/library/ModuleLibraryPlugin.js +38 -1
- package/lib/loaders/LoaderRunner.js +714 -0
- package/lib/loaders/loadLoader.js +100 -0
- package/lib/node/ReadFileCompileAsyncWasmPlugin.js +19 -0
- package/lib/node/ReadFileCompileWasmPlugin.js +14 -0
- package/lib/optimize/ConcatenatedModule.js +120 -16
- package/lib/optimize/FlagIncludedChunksPlugin.js +13 -3
- package/lib/optimize/InnerGraphPlugin.js +50 -30
- package/lib/optimize/ModuleConcatenationPlugin.js +69 -3
- package/lib/optimize/SideEffectsFlagPlugin.js +86 -43
- package/lib/prefetch/ChunkPrefetchPreloadPlugin.js +15 -0
- package/lib/prefetch/ChunkPreloadTriggerRuntimeModule.js +24 -13
- package/lib/prefetch/ResourceHintPlugin.js +663 -0
- package/lib/prefetch/ResourceHintRuntimeModule.js +149 -0
- package/lib/prefetch/StartupAssetHintRuntimeModule.js +210 -0
- package/lib/prefetch/parseResourceHintOptions.js +103 -0
- package/lib/rules/RuleSetCompiler.js +114 -0
- package/lib/runtime/AsyncModuleGeneratorRuntimeModule.js +56 -0
- package/lib/runtime/AsyncModuleRuntimeModule.js +24 -8
- package/lib/runtime/AutoPublicPathRuntimeModule.js +7 -1
- package/lib/runtime/CommonJsWrapRuntimeModule.js +37 -0
- package/lib/runtime/GetWorkletBootstrapRuntimeModule.js +59 -0
- package/lib/runtime/MakeDeferredNamespaceObjectRuntime.js +204 -8
- package/lib/runtime/SetAnonymousDefaultNameRuntimeModule.js +4 -1
- package/lib/schemes/HttpUriPlugin.js +40 -1
- package/lib/schemes/VirtualUrlPlugin.js +1 -2
- package/lib/serialization/FileMiddleware.js +29 -3
- package/lib/stats/DefaultStatsFactoryPlugin.js +32 -3
- package/lib/stats/DefaultStatsPresetPlugin.js +2 -0
- package/lib/stats/DefaultStatsPrinterPlugin.js +12 -2
- package/lib/stats/StatsFactory.js +15 -8
- package/lib/url/URLParserPlugin.js +98 -19
- package/lib/util/AsyncQueue.js +122 -72
- package/lib/util/LocConverter.js +9 -8
- package/lib/util/SetHelpers.js +1 -1
- package/lib/util/SourceProcessor.js +41 -28
- package/lib/util/StackedMap.js +122 -48
- package/lib/util/binarySearchBounds.js +2 -2
- package/lib/util/concatenate.js +40 -14
- package/lib/util/createHooksRegistry.js +13 -5
- package/lib/util/dataURL.js +2 -2
- package/lib/util/deterministicGrouping.js +7 -5
- package/lib/util/formatSize.js +6 -2
- package/lib/util/globUtils.js +710 -0
- package/lib/util/identifier.js +23 -6
- package/lib/util/implicitTypeLoaderFallback.js +62 -0
- package/lib/util/internalSerializables.js +88 -71
- package/lib/util/magicComment.js +121 -25
- package/lib/util/numberHash.js +2 -2
- package/lib/wasm-async/AsyncWasmCompileRuntimeModule.js +24 -18
- package/lib/wasm-async/AsyncWasmLoadingRuntimeModule.js +33 -22
- package/lib/wasm-sync/WasmChunkLoadingRuntimeModule.js +79 -16
- package/lib/web/FetchCompileAsyncWasmPlugin.js +19 -0
- package/lib/web/FetchCompileWasmPlugin.js +14 -0
- package/lib/web/JsonpChunkLoadingRuntimeModule.js +2 -0
- package/lib/webpack.js +65 -0
- package/lib/webworker/ImportScriptsChunkLoadingRuntimeModule.js +3 -0
- package/module.d.ts +21 -0
- package/package.json +14 -13
- package/schemas/WebpackOptions.check.js +1 -1
- package/schemas/WebpackOptions.json +759 -36
- package/schemas/plugins/HtmlParserOptions.check.js +1 -1
- package/schemas/plugins/ProgressPlugin.check.js +1 -1
- package/schemas/plugins/ProgressPlugin.json +17 -1
- package/schemas/plugins/container/ContainerReferencePlugin.check.js +1 -1
- package/schemas/plugins/container/ContainerReferencePlugin.json +1 -0
- package/schemas/plugins/container/ExternalsType.check.js +1 -1
- package/schemas/plugins/container/ModuleFederationPlugin.check.js +1 -1
- package/schemas/plugins/container/ModuleFederationPlugin.json +1 -0
- package/schemas/plugins/css/CssAutoOrModuleParserOptions.check.js +1 -1
- package/schemas/plugins/css/CssModuleParserOptions.check.js +1 -1
- package/schemas/plugins/css/CssParserOptions.check.js +1 -1
- package/types.d.ts +1300 -325
|
@@ -15,16 +15,19 @@ const memoize = require("../util/memoize");
|
|
|
15
15
|
/** @typedef {import("../javascript/JavascriptParser")} JavascriptParser */
|
|
16
16
|
/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */
|
|
17
17
|
/** @typedef {import("./CommonJsRequireDependency")} CommonJsRequireDependency */
|
|
18
|
+
/** @typedef {import("./HarmonyEvaluatedImportSpecifierDependency")} HarmonyEvaluatedImportSpecifierDependency */
|
|
18
19
|
/** @typedef {import("./HarmonyImportSpecifierDependency")} HarmonyImportSpecifierDependency */
|
|
19
20
|
/** @typedef {import("./ImportDependency")} ImportDependency */
|
|
20
21
|
|
|
21
22
|
// Tuple-encoded boolean formula over guard dependencies. Split into per-shape
|
|
22
23
|
// aliases so the recursive references resolve through array/object types.
|
|
24
|
+
// `v` = dependency-liveness atom, `p` = `"x" in ns` presence atom.
|
|
23
25
|
/** @typedef {["v", Dependency]} GuardAtom */
|
|
26
|
+
/** @typedef {["p", HarmonyEvaluatedImportSpecifierDependency]} GuardPresenceAtom */
|
|
24
27
|
/** @typedef {["?"]} GuardUnknown */
|
|
25
28
|
/** @typedef {["!", GuardFormula]} GuardNot */
|
|
26
29
|
/** @typedef {["&&" | "||" | "??", GuardFormula, GuardFormula]} GuardLogical */
|
|
27
|
-
/** @typedef {GuardAtom | GuardUnknown | GuardNot | GuardLogical} GuardFormula */
|
|
30
|
+
/** @typedef {GuardAtom | GuardPresenceAtom | GuardUnknown | GuardNot | GuardLogical} GuardFormula */
|
|
28
31
|
/** @typedef {{ formula: GuardFormula, value: boolean }} DependencyGuard branch guard: the dependency is live only when the formula evaluates to `value` */
|
|
29
32
|
/** @typedef {HarmonyImportSpecifierDependency | CommonJsRequireDependency | ImportDependency} GuardableDependency */
|
|
30
33
|
|
|
@@ -33,16 +36,19 @@ const memoize = require("../util/memoize");
|
|
|
33
36
|
* conditional branch body. Carries the `"x" in ns` presence guards and/or the
|
|
34
37
|
* dead-branch dependency guard for that branch.
|
|
35
38
|
* @typedef {object} GuardFrame
|
|
36
|
-
* @property {Map<string, Set<string>>=} presence `"x" in ns` presence guards active in this branch
|
|
37
39
|
* @property {Expression=} test the conditional test (for the lazily built formula)
|
|
38
40
|
* @property {number=} depStart dependency count before the test was walked
|
|
39
41
|
* @property {boolean=} condition branch truthiness the dependency guard is live for
|
|
40
|
-
* @property {GuardFormula | null=} formula memoized formula (null = no knowable atom)
|
|
42
|
+
* @property {GuardFormula | null=} formula memoized dependency-guard formula (null = no knowable atom)
|
|
43
|
+
* @property {GuardFormula | null=} presenceFormula memoized presence formula (null = no presence atom)
|
|
41
44
|
*/
|
|
42
45
|
|
|
43
46
|
const getHarmonyImportSpecifierDependency = memoize(() =>
|
|
44
47
|
require("./HarmonyImportSpecifierDependency")
|
|
45
48
|
);
|
|
49
|
+
const getHarmonyEvaluatedImportSpecifierDependency = memoize(() =>
|
|
50
|
+
require("./HarmonyEvaluatedImportSpecifierDependency")
|
|
51
|
+
);
|
|
46
52
|
|
|
47
53
|
// Tri-state truthiness: UNKNOWN means not statically known.
|
|
48
54
|
const UNKNOWN = 0;
|
|
@@ -62,12 +68,12 @@ const flip = (t) => (t === TRUE ? FALSE : t === FALSE ? TRUE : UNKNOWN);
|
|
|
62
68
|
const fromBool = (b) => (b ? TRUE : FALSE);
|
|
63
69
|
|
|
64
70
|
/**
|
|
65
|
-
* Build a
|
|
71
|
+
* Build a liveness formula from a conditional test AST.
|
|
66
72
|
* @param {Expression} test conditional test expression
|
|
67
73
|
* @param {Map<number, HarmonyImportSpecifierDependency>} depByRangeStart import-specifier deps in the test, keyed by range start
|
|
68
74
|
* @returns {GuardFormula | null} formula, or null when it has no knowable atom
|
|
69
75
|
*/
|
|
70
|
-
const
|
|
76
|
+
const buildLivenessFormula = (test, depByRangeStart) => {
|
|
71
77
|
/**
|
|
72
78
|
* @param {Expression} node ast node
|
|
73
79
|
* @returns {GuardFormula} formula node
|
|
@@ -104,6 +110,7 @@ const buildGuardFormula = (test, depByRangeStart) => {
|
|
|
104
110
|
const hasAtom = (formula) => {
|
|
105
111
|
switch (formula[0]) {
|
|
106
112
|
case "v":
|
|
113
|
+
case "p":
|
|
107
114
|
return true;
|
|
108
115
|
case "!":
|
|
109
116
|
return hasAtom(formula[1]);
|
|
@@ -122,7 +129,7 @@ const hasAtom = (formula) => {
|
|
|
122
129
|
* @param {RuntimeSpec} runtime runtime
|
|
123
130
|
* @returns {{ t: number, n: number }} truthy `t` and null `n` tri-states
|
|
124
131
|
*/
|
|
125
|
-
const
|
|
132
|
+
const evalLivenessFormula = (formula, moduleGraph, runtime) => {
|
|
126
133
|
switch (formula[0]) {
|
|
127
134
|
case "v": {
|
|
128
135
|
const dep = /** @type {HarmonyImportSpecifierDependency} */ (formula[1]);
|
|
@@ -145,12 +152,12 @@ const evalNode = (formula, moduleGraph, runtime) => {
|
|
|
145
152
|
case "!":
|
|
146
153
|
// `!x` always yields a boolean → never nullish.
|
|
147
154
|
return {
|
|
148
|
-
t: flip(
|
|
155
|
+
t: flip(evalLivenessFormula(formula[1], moduleGraph, runtime).t),
|
|
149
156
|
n: FALSE
|
|
150
157
|
};
|
|
151
158
|
case "&&": {
|
|
152
|
-
const l =
|
|
153
|
-
const r =
|
|
159
|
+
const l = evalLivenessFormula(formula[1], moduleGraph, runtime);
|
|
160
|
+
const r = evalLivenessFormula(formula[2], moduleGraph, runtime);
|
|
154
161
|
const t =
|
|
155
162
|
l.t === FALSE || r.t === FALSE
|
|
156
163
|
? FALSE
|
|
@@ -160,8 +167,8 @@ const evalNode = (formula, moduleGraph, runtime) => {
|
|
|
160
167
|
return { t, n: UNKNOWN };
|
|
161
168
|
}
|
|
162
169
|
case "||": {
|
|
163
|
-
const l =
|
|
164
|
-
const r =
|
|
170
|
+
const l = evalLivenessFormula(formula[1], moduleGraph, runtime);
|
|
171
|
+
const r = evalLivenessFormula(formula[2], moduleGraph, runtime);
|
|
165
172
|
const t =
|
|
166
173
|
l.t === TRUE || r.t === TRUE
|
|
167
174
|
? TRUE
|
|
@@ -171,8 +178,8 @@ const evalNode = (formula, moduleGraph, runtime) => {
|
|
|
171
178
|
return { t, n: UNKNOWN };
|
|
172
179
|
}
|
|
173
180
|
case "??": {
|
|
174
|
-
const l =
|
|
175
|
-
const r =
|
|
181
|
+
const l = evalLivenessFormula(formula[1], moduleGraph, runtime);
|
|
182
|
+
const r = evalLivenessFormula(formula[2], moduleGraph, runtime);
|
|
176
183
|
// `l ?? r` is l when l non-nullish, else r.
|
|
177
184
|
const t =
|
|
178
185
|
l.n === FALSE ? l.t : l.n === TRUE ? r.t : l.t === r.t ? l.t : UNKNOWN;
|
|
@@ -192,37 +199,201 @@ const evalNode = (formula, moduleGraph, runtime) => {
|
|
|
192
199
|
*/
|
|
193
200
|
const isDeadByGuards = (guards, moduleGraph, runtime) => {
|
|
194
201
|
for (const guard of guards) {
|
|
195
|
-
const t =
|
|
202
|
+
const t = evalLivenessFormula(guard.formula, moduleGraph, runtime).t;
|
|
196
203
|
if (t !== UNKNOWN && t !== (guard.value ? TRUE : FALSE)) return true;
|
|
197
204
|
}
|
|
198
205
|
return false;
|
|
199
206
|
};
|
|
200
207
|
|
|
201
208
|
/**
|
|
202
|
-
* Builds (once) the
|
|
203
|
-
*
|
|
209
|
+
* Builds (once) the liveness formula for a frame from the import specifier deps
|
|
210
|
+
* created while walking the test.
|
|
204
211
|
* @param {JavascriptParser} parser the parser
|
|
205
212
|
* @param {GuardFrame} frame guard frame
|
|
206
213
|
* @returns {GuardFormula | null} formula, or null when it has no knowable atom
|
|
207
214
|
*/
|
|
208
|
-
const
|
|
215
|
+
const buildFrameLivenessFormula = (parser, frame) => {
|
|
209
216
|
const HarmonyImportSpecifierDependency =
|
|
210
217
|
getHarmonyImportSpecifierDependency();
|
|
218
|
+
const HarmonyEvaluatedImportSpecifierDependency =
|
|
219
|
+
getHarmonyEvaluatedImportSpecifierDependency();
|
|
211
220
|
const deps = /** @type {Module} */ (parser.state.module).dependencies;
|
|
212
221
|
/** @type {Map<number, HarmonyImportSpecifierDependency>} */
|
|
213
222
|
const depByRangeStart = new Map();
|
|
214
223
|
for (let i = /** @type {number} */ (frame.depStart); i < deps.length; i++) {
|
|
215
224
|
const dep = deps[i];
|
|
216
|
-
|
|
225
|
+
// Exclude `"x" in ns` evaluated deps; those feed the presence formula only.
|
|
226
|
+
if (
|
|
227
|
+
dep instanceof HarmonyImportSpecifierDependency &&
|
|
228
|
+
!(dep instanceof HarmonyEvaluatedImportSpecifierDependency) &&
|
|
229
|
+
dep.range
|
|
230
|
+
) {
|
|
231
|
+
depByRangeStart.set(dep.range[0], dep);
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
return buildLivenessFormula(
|
|
235
|
+
/** @type {Expression} */ (frame.test),
|
|
236
|
+
depByRangeStart
|
|
237
|
+
);
|
|
238
|
+
};
|
|
239
|
+
|
|
240
|
+
/**
|
|
241
|
+
* Build a presence formula from a conditional test AST. Statically-decided
|
|
242
|
+
* `||`/`??` operands are folded away at build time, so the result contains only
|
|
243
|
+
* `"x" in ns` presence atoms (plus `&&`/`!`).
|
|
244
|
+
* @param {JavascriptParser} parser the parser
|
|
245
|
+
* @param {Expression} test conditional test expression
|
|
246
|
+
* @param {Map<number, HarmonyEvaluatedImportSpecifierDependency>} depByRangeStart in-operator deps in the test, keyed by range start
|
|
247
|
+
* @returns {GuardFormula | null} formula, or null when it has no presence atom
|
|
248
|
+
*/
|
|
249
|
+
const buildPresenceFormula = (parser, test, depByRangeStart) => {
|
|
250
|
+
/**
|
|
251
|
+
* @param {Expression} node ast node
|
|
252
|
+
* @returns {GuardFormula} formula node
|
|
253
|
+
*/
|
|
254
|
+
const build = (node) => {
|
|
255
|
+
if (node.type === "UnaryExpression" && node.operator === "!") {
|
|
256
|
+
return ["!", build(/** @type {Expression} */ (node.argument))];
|
|
257
|
+
}
|
|
258
|
+
if (node.type === "LogicalExpression") {
|
|
259
|
+
if (node.operator === "&&") {
|
|
260
|
+
return [
|
|
261
|
+
"&&",
|
|
262
|
+
build(/** @type {Expression} */ (node.left)),
|
|
263
|
+
build(/** @type {Expression} */ (node.right))
|
|
264
|
+
];
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
if (node.operator === "||") {
|
|
268
|
+
if (parser.evaluateExpression(node.left).asBool() === false) {
|
|
269
|
+
return build(/** @type {Expression} */ (node.right));
|
|
270
|
+
}
|
|
271
|
+
if (parser.evaluateExpression(node.right).asBool() === false) {
|
|
272
|
+
return build(/** @type {Expression} */ (node.left));
|
|
273
|
+
}
|
|
274
|
+
return ["?"];
|
|
275
|
+
}
|
|
276
|
+
|
|
277
|
+
if (node.operator === "??") {
|
|
278
|
+
const nullish = parser.evaluateExpression(node.left).asNullish();
|
|
279
|
+
if (nullish === true) {
|
|
280
|
+
return build(/** @type {Expression} */ (node.right));
|
|
281
|
+
}
|
|
282
|
+
if (nullish === false) {
|
|
283
|
+
return build(/** @type {Expression} */ (node.left));
|
|
284
|
+
}
|
|
285
|
+
return ["?"];
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
const dep =
|
|
289
|
+
node.range && depByRangeStart.get(/** @type {number} */ (node.range[0]));
|
|
290
|
+
return dep ? ["p", dep] : ["?"];
|
|
291
|
+
};
|
|
292
|
+
|
|
293
|
+
const formula = build(test);
|
|
294
|
+
return hasAtom(formula) ? formula : null;
|
|
295
|
+
};
|
|
296
|
+
|
|
297
|
+
/**
|
|
298
|
+
* Whether a presence formula guarantees `ns.member` is present. "Must be truthy"
|
|
299
|
+
* semantics: the member is guaranteed when some `"member" in ns` atom must hold
|
|
300
|
+
* for the branch condition. Statically-dead branches never reach here — the
|
|
301
|
+
* parser eliminates them before the branch body is walked.
|
|
302
|
+
* @param {GuardFormula} formula presence formula
|
|
303
|
+
* @param {string} name namespace binding name
|
|
304
|
+
* @param {string} member member key
|
|
305
|
+
* @param {boolean} needTruthy whether the formula must be truthy
|
|
306
|
+
* @returns {boolean} true when the member is guaranteed present
|
|
307
|
+
*/
|
|
308
|
+
const evalPresenceFormula = (formula, name, member, needTruthy) => {
|
|
309
|
+
switch (formula[0]) {
|
|
310
|
+
case "p": {
|
|
311
|
+
const dep = /** @type {HarmonyEvaluatedImportSpecifierDependency} */ (
|
|
312
|
+
formula[1]
|
|
313
|
+
);
|
|
314
|
+
return (
|
|
315
|
+
needTruthy &&
|
|
316
|
+
dep.directImport === true &&
|
|
317
|
+
dep.name === name &&
|
|
318
|
+
dep.ids.length === 1 &&
|
|
319
|
+
dep.ids[0] === member
|
|
320
|
+
);
|
|
321
|
+
}
|
|
322
|
+
case "!":
|
|
323
|
+
return evalPresenceFormula(formula[1], name, member, !needTruthy);
|
|
324
|
+
case "&&":
|
|
325
|
+
return (
|
|
326
|
+
needTruthy &&
|
|
327
|
+
(evalPresenceFormula(formula[1], name, member, true) ||
|
|
328
|
+
evalPresenceFormula(formula[2], name, member, true))
|
|
329
|
+
);
|
|
330
|
+
default:
|
|
331
|
+
return false;
|
|
332
|
+
}
|
|
333
|
+
};
|
|
334
|
+
|
|
335
|
+
/**
|
|
336
|
+
* Builds (once) the presence formula for a frame from the in-operator deps
|
|
337
|
+
* created while walking the test.
|
|
338
|
+
* @param {JavascriptParser} parser the parser
|
|
339
|
+
* @param {GuardFrame} frame guard frame
|
|
340
|
+
* @returns {GuardFormula | null} formula, or null when it has no presence atom
|
|
341
|
+
*/
|
|
342
|
+
const buildFramePresenceFormula = (parser, frame) => {
|
|
343
|
+
const HarmonyEvaluatedImportSpecifierDependency =
|
|
344
|
+
getHarmonyEvaluatedImportSpecifierDependency();
|
|
345
|
+
const deps = /** @type {Module} */ (parser.state.module).dependencies;
|
|
346
|
+
/** @type {Map<number, HarmonyEvaluatedImportSpecifierDependency>} */
|
|
347
|
+
const depByRangeStart = new Map();
|
|
348
|
+
for (let i = /** @type {number} */ (frame.depStart); i < deps.length; i++) {
|
|
349
|
+
const dep = deps[i];
|
|
350
|
+
if (dep instanceof HarmonyEvaluatedImportSpecifierDependency && dep.range) {
|
|
217
351
|
depByRangeStart.set(dep.range[0], dep);
|
|
218
352
|
}
|
|
219
353
|
}
|
|
220
|
-
return
|
|
354
|
+
return buildPresenceFormula(
|
|
355
|
+
parser,
|
|
221
356
|
/** @type {Expression} */ (frame.test),
|
|
222
357
|
depByRangeStart
|
|
223
358
|
);
|
|
224
359
|
};
|
|
225
360
|
|
|
361
|
+
/**
|
|
362
|
+
* Whether an active presence guard proves `ns.member` present, suppressing
|
|
363
|
+
* export-presence errors. Each frame is evaluated against its branch condition,
|
|
364
|
+
* so the `else` of `if (!("x" in ns))` also guards `ns.x`.
|
|
365
|
+
* @param {JavascriptParser} parser the parser
|
|
366
|
+
* @param {GuardFrame[]} stack the guard stack
|
|
367
|
+
* @param {string} name namespace binding name
|
|
368
|
+
* @param {string} member member key
|
|
369
|
+
* @returns {boolean} true when a guard proves the member present
|
|
370
|
+
*/
|
|
371
|
+
const isPresentByGuards = (parser, stack, name, member) => {
|
|
372
|
+
for (let i = stack.length - 1; i >= 0; i--) {
|
|
373
|
+
const frame = stack[i];
|
|
374
|
+
if (frame.depStart === undefined) continue;
|
|
375
|
+
let formula = frame.presenceFormula;
|
|
376
|
+
if (formula === undefined) {
|
|
377
|
+
formula = frame.presenceFormula = buildFramePresenceFormula(
|
|
378
|
+
parser,
|
|
379
|
+
frame
|
|
380
|
+
);
|
|
381
|
+
}
|
|
382
|
+
if (
|
|
383
|
+
formula !== null &&
|
|
384
|
+
evalPresenceFormula(
|
|
385
|
+
formula,
|
|
386
|
+
name,
|
|
387
|
+
member,
|
|
388
|
+
/** @type {boolean} */ (frame.condition)
|
|
389
|
+
)
|
|
390
|
+
) {
|
|
391
|
+
return true;
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
return false;
|
|
395
|
+
};
|
|
396
|
+
|
|
226
397
|
/**
|
|
227
398
|
* Tags a freshly created dependency with the active dependency guards.
|
|
228
399
|
* @param {JavascriptParser} parser the parser
|
|
@@ -239,7 +410,7 @@ const attachDependencyGuards = (parser, dep) => {
|
|
|
239
410
|
if (frame.depStart === undefined) continue;
|
|
240
411
|
let formula = frame.formula;
|
|
241
412
|
if (formula === undefined) {
|
|
242
|
-
formula = frame.formula =
|
|
413
|
+
formula = frame.formula = buildFrameLivenessFormula(parser, frame);
|
|
243
414
|
}
|
|
244
415
|
if (formula === null) continue;
|
|
245
416
|
(guards || (guards = [])).push({
|
|
@@ -252,3 +423,4 @@ const attachDependencyGuards = (parser, dep) => {
|
|
|
252
423
|
|
|
253
424
|
module.exports.attachDependencyGuards = attachDependencyGuards;
|
|
254
425
|
module.exports.isDeadByGuards = isDeadByGuards;
|
|
426
|
+
module.exports.isPresentByGuards = isPresentByGuards;
|
|
@@ -25,6 +25,7 @@ const HarmonyImportSideEffectDependency = require("./HarmonyImportSideEffectDepe
|
|
|
25
25
|
const HarmonyImportSpecifierDependency = require("./HarmonyImportSpecifierDependency");
|
|
26
26
|
|
|
27
27
|
const HarmonyTopLevelThisParserPlugin = require("./HarmonyTopLevelThisParserPlugin");
|
|
28
|
+
const TopLevelAwaitDependency = require("./TopLevelAwaitDependency");
|
|
28
29
|
|
|
29
30
|
/** @typedef {import("../../declarations/WebpackOptions").JavascriptParserOptions} JavascriptParserOptions */
|
|
30
31
|
/** @typedef {import("../Compiler")} Compiler */
|
|
@@ -62,6 +63,11 @@ class HarmonyModulesPlugin {
|
|
|
62
63
|
new HarmonyCompatibilityDependency.Template()
|
|
63
64
|
);
|
|
64
65
|
|
|
66
|
+
compilation.dependencyTemplates.set(
|
|
67
|
+
TopLevelAwaitDependency,
|
|
68
|
+
new TopLevelAwaitDependency.Template()
|
|
69
|
+
);
|
|
70
|
+
|
|
65
71
|
compilation.dependencyFactories.set(
|
|
66
72
|
HarmonyImportSideEffectDependency,
|
|
67
73
|
normalModuleFactory
|
|
@@ -29,7 +29,7 @@ class HarmonyTopLevelThisParserPlugin {
|
|
|
29
29
|
/** @type {Range} */ (node.range),
|
|
30
30
|
null
|
|
31
31
|
);
|
|
32
|
-
dep.loc =
|
|
32
|
+
dep.loc = parser.getLocation(node);
|
|
33
33
|
parser.state.module.addPresentationalDependency(dep);
|
|
34
34
|
return true;
|
|
35
35
|
}
|