webpack 5.27.2 → 5.31.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.
- package/lib/Compiler.js +4 -0
- package/lib/Dependency.js +4 -0
- package/lib/ExportsInfo.js +62 -28
- package/lib/FileSystemInfo.js +206 -43
- package/lib/FlagDependencyExportsPlugin.js +12 -3
- package/lib/NormalModule.js +4 -0
- package/lib/WebpackOptionsApply.js +24 -7
- package/lib/asset/AssetGenerator.js +84 -12
- package/lib/asset/AssetModulesPlugin.js +3 -0
- package/lib/cache/IdleFileCachePlugin.js +26 -16
- package/lib/cache/MemoryCachePlugin.js +6 -0
- package/lib/cache/MemoryWithGcCachePlugin.js +129 -0
- package/lib/cache/PackFileCacheStrategy.js +97 -15
- package/lib/config/defaults.js +16 -4
- package/lib/config/normalization.js +6 -2
- package/lib/dependencies/HarmonyExportExpressionDependency.js +1 -0
- package/lib/dependencies/HarmonyExportImportedSpecifierDependency.js +5 -0
- package/lib/dependencies/HarmonyExportSpecifierDependency.js +1 -0
- package/lib/hmr/HotModuleReplacement.runtime.js +3 -2
- package/lib/hmr/JavascriptHotModuleReplacement.runtime.js +1 -1
- package/lib/index.js +28 -0
- package/lib/javascript/JavascriptParser.js +4 -0
- package/lib/logging/createConsoleLogger.js +19 -1
- package/lib/node/NodeEnvironmentPlugin.js +18 -11
- package/lib/node/nodeConsole.js +121 -112
- package/lib/serialization/ObjectMiddleware.js +50 -30
- package/lib/stats/DefaultStatsFactoryPlugin.js +2 -2
- package/lib/util/deterministicGrouping.js +38 -4
- package/lib/util/runtime.js +1 -1
- package/package.json +2 -2
- package/schemas/WebpackOptions.json +50 -1
- package/types.d.ts +155 -18
@@ -121,13 +121,16 @@ const getNormalizedWebpackOptions = config => {
|
|
121
121
|
if (cache === false) return false;
|
122
122
|
if (cache === true) {
|
123
123
|
return {
|
124
|
-
type: "memory"
|
124
|
+
type: "memory",
|
125
|
+
maxGenerations: undefined
|
125
126
|
};
|
126
127
|
}
|
127
128
|
switch (cache.type) {
|
128
129
|
case "filesystem":
|
129
130
|
return {
|
130
131
|
type: "filesystem",
|
132
|
+
maxMemoryGenerations: cache.maxMemoryGenerations,
|
133
|
+
maxAge: cache.maxAge,
|
131
134
|
buildDependencies: cloneObject(cache.buildDependencies),
|
132
135
|
cacheDirectory: cache.cacheDirectory,
|
133
136
|
cacheLocation: cache.cacheLocation,
|
@@ -141,7 +144,8 @@ const getNormalizedWebpackOptions = config => {
|
|
141
144
|
case undefined:
|
142
145
|
case "memory":
|
143
146
|
return {
|
144
|
-
type: "memory"
|
147
|
+
type: "memory",
|
148
|
+
maxGenerations: cache.maxGenerations
|
145
149
|
};
|
146
150
|
default:
|
147
151
|
// @ts-expect-error Property 'type' does not exist on type 'never'. ts(2339)
|
@@ -543,6 +543,7 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
|
|
543
543
|
export: item.ids,
|
544
544
|
hidden: item.hidden
|
545
545
|
})),
|
546
|
+
priority: 1,
|
546
547
|
dependencies: [from.module]
|
547
548
|
};
|
548
549
|
}
|
@@ -557,6 +558,7 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
|
|
557
558
|
export: ["default"]
|
558
559
|
}
|
559
560
|
],
|
561
|
+
priority: 1,
|
560
562
|
dependencies: [from.module]
|
561
563
|
};
|
562
564
|
}
|
@@ -584,6 +586,7 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
|
|
584
586
|
]
|
585
587
|
}
|
586
588
|
],
|
589
|
+
priority: 1,
|
587
590
|
dependencies: [from.module]
|
588
591
|
};
|
589
592
|
}
|
@@ -597,6 +600,7 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
|
|
597
600
|
export: null
|
598
601
|
}
|
599
602
|
],
|
603
|
+
priority: 1,
|
600
604
|
dependencies: [from.module]
|
601
605
|
};
|
602
606
|
}
|
@@ -610,6 +614,7 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
|
|
610
614
|
export: ["default"]
|
611
615
|
}
|
612
616
|
],
|
617
|
+
priority: 1,
|
613
618
|
dependencies: [from.module]
|
614
619
|
};
|
615
620
|
}
|
@@ -101,6 +101,7 @@ module.exports = function () {
|
|
101
101
|
}
|
102
102
|
|
103
103
|
function createModuleHotObject(moduleId, me) {
|
104
|
+
var _main = currentChildModule !== moduleId;
|
104
105
|
var hot = {
|
105
106
|
// private stuff
|
106
107
|
_acceptedDependencies: {},
|
@@ -110,10 +111,10 @@ module.exports = function () {
|
|
110
111
|
_selfDeclined: false,
|
111
112
|
_selfInvalidated: false,
|
112
113
|
_disposeHandlers: [],
|
113
|
-
_main:
|
114
|
+
_main: _main,
|
114
115
|
_requireSelf: function () {
|
115
116
|
currentParents = me.parents.slice();
|
116
|
-
currentChildModule = moduleId;
|
117
|
+
currentChildModule = _main ? undefined : moduleId;
|
117
118
|
__webpack_require__(moduleId);
|
118
119
|
},
|
119
120
|
|
@@ -207,7 +207,7 @@ module.exports = function () {
|
|
207
207
|
var module = $moduleCache$[outdatedModuleId];
|
208
208
|
if (
|
209
209
|
module &&
|
210
|
-
module.hot._selfAccepted &&
|
210
|
+
(module.hot._selfAccepted || module.hot._main) &&
|
211
211
|
// removed self-accepted modules should not be required
|
212
212
|
appliedUpdate[outdatedModuleId] !== warnUnexpectedRequire &&
|
213
213
|
// when called invalidate self-accepting is not possible
|
package/lib/index.js
CHANGED
@@ -28,7 +28,20 @@ const memoize = require("./util/memoize");
|
|
28
28
|
/** @typedef {import("./MultiStats")} MultiStats */
|
29
29
|
/** @typedef {import("./Parser").ParserState} ParserState */
|
30
30
|
/** @typedef {import("./Watching")} Watching */
|
31
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsAsset} StatsAsset */
|
32
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunk} StatsChunk */
|
33
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkGroup} StatsChunkGroup */
|
34
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsChunkOrigin} StatsChunkOrigin */
|
31
35
|
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsCompilation} StatsCompilation */
|
36
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsError} StatsError */
|
37
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLogging} StatsLogging */
|
38
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsLoggingEntry} StatsLoggingEntry */
|
39
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModule} StatsModule */
|
40
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleIssuer} StatsModuleIssuer */
|
41
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleReason} StatsModuleReason */
|
42
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceDependency} StatsModuleTraceDependency */
|
43
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsModuleTraceItem} StatsModuleTraceItem */
|
44
|
+
/** @typedef {import("./stats/DefaultStatsFactoryPlugin").StatsProfile} StatsProfile */
|
32
45
|
|
33
46
|
/**
|
34
47
|
* @template {Function} T
|
@@ -101,6 +114,9 @@ module.exports = mergeExports(fn, {
|
|
101
114
|
get AutomaticPrefetchPlugin() {
|
102
115
|
return require("./AutomaticPrefetchPlugin");
|
103
116
|
},
|
117
|
+
get AsyncDependenciesBlock() {
|
118
|
+
return require("./AsyncDependenciesBlock");
|
119
|
+
},
|
104
120
|
get BannerPlugin() {
|
105
121
|
return require("./BannerPlugin");
|
106
122
|
},
|
@@ -305,6 +321,18 @@ module.exports = mergeExports(fn, {
|
|
305
321
|
}
|
306
322
|
},
|
307
323
|
|
324
|
+
dependencies: {
|
325
|
+
get ModuleDependency() {
|
326
|
+
return require("./dependencies/ModuleDependency");
|
327
|
+
},
|
328
|
+
get ConstDependency() {
|
329
|
+
return require("./dependencies/ConstDependency");
|
330
|
+
},
|
331
|
+
get NullDependency() {
|
332
|
+
return require("./dependencies/NullDependency");
|
333
|
+
}
|
334
|
+
},
|
335
|
+
|
308
336
|
ids: {
|
309
337
|
get ChunkModuleIdRangePlugin() {
|
310
338
|
return require("./ids/ChunkModuleIdRangePlugin");
|
@@ -942,6 +942,10 @@ class JavascriptParser extends Parser {
|
|
942
942
|
.setRange(expr.range);
|
943
943
|
}
|
944
944
|
});
|
945
|
+
this.hooks.finish.tap("JavascriptParser", () => {
|
946
|
+
// Cleanup for GC
|
947
|
+
cachedExpression = cachedInfo = undefined;
|
948
|
+
});
|
945
949
|
};
|
946
950
|
tapEvaluateWithVariableInfo("Identifier", expr => {
|
947
951
|
const info = this.getVariableInfo(
|
@@ -13,11 +13,29 @@ const { LogType } = require("./Logger");
|
|
13
13
|
|
14
14
|
/** @typedef {function(string): boolean} FilterFunction */
|
15
15
|
|
16
|
+
/**
|
17
|
+
* @typedef {Object} LoggerConsole
|
18
|
+
* @property {function(): void} clear
|
19
|
+
* @property {function(): void} trace
|
20
|
+
* @property {(...args: any[]) => void} info
|
21
|
+
* @property {(...args: any[]) => void} log
|
22
|
+
* @property {(...args: any[]) => void} warn
|
23
|
+
* @property {(...args: any[]) => void} error
|
24
|
+
* @property {(...args: any[]) => void=} debug
|
25
|
+
* @property {(...args: any[]) => void=} group
|
26
|
+
* @property {(...args: any[]) => void=} groupCollapsed
|
27
|
+
* @property {(...args: any[]) => void=} groupEnd
|
28
|
+
* @property {(...args: any[]) => void=} status
|
29
|
+
* @property {(...args: any[]) => void=} profile
|
30
|
+
* @property {(...args: any[]) => void=} profileEnd
|
31
|
+
* @property {(...args: any[]) => void=} logTime
|
32
|
+
*/
|
33
|
+
|
16
34
|
/**
|
17
35
|
* @typedef {Object} LoggerOptions
|
18
36
|
* @property {false|true|"none"|"error"|"warn"|"info"|"log"|"verbose"} level loglevel
|
19
37
|
* @property {FilterTypes|boolean} debug filter for debug logging
|
20
|
-
* @property {
|
38
|
+
* @property {LoggerConsole} console the console to log to
|
21
39
|
*/
|
22
40
|
|
23
41
|
/**
|
@@ -11,11 +11,16 @@ const createConsoleLogger = require("../logging/createConsoleLogger");
|
|
11
11
|
const NodeWatchFileSystem = require("./NodeWatchFileSystem");
|
12
12
|
const nodeConsole = require("./nodeConsole");
|
13
13
|
|
14
|
+
/** @typedef {import("../../declarations/WebpackOptions").InfrastructureLogging} InfrastructureLogging */
|
14
15
|
/** @typedef {import("../Compiler")} Compiler */
|
15
16
|
|
16
17
|
class NodeEnvironmentPlugin {
|
18
|
+
/**
|
19
|
+
* @param {Object} options options
|
20
|
+
* @param {InfrastructureLogging} options.infrastructureLogging infrastructure logging options
|
21
|
+
*/
|
17
22
|
constructor(options) {
|
18
|
-
this.options = options
|
23
|
+
this.options = options;
|
19
24
|
}
|
20
25
|
|
21
26
|
/**
|
@@ -24,16 +29,18 @@ class NodeEnvironmentPlugin {
|
|
24
29
|
* @returns {void}
|
25
30
|
*/
|
26
31
|
apply(compiler) {
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
32
|
+
const { infrastructureLogging } = this.options;
|
33
|
+
compiler.infrastructureLogger = createConsoleLogger({
|
34
|
+
level: infrastructureLogging.level || "info",
|
35
|
+
debug: infrastructureLogging.debug || false,
|
36
|
+
console:
|
37
|
+
infrastructureLogging.console ||
|
38
|
+
nodeConsole({
|
39
|
+
colors: infrastructureLogging.colors,
|
40
|
+
appendOnly: infrastructureLogging.appendOnly,
|
41
|
+
stream: infrastructureLogging.stream
|
42
|
+
})
|
43
|
+
});
|
37
44
|
compiler.inputFileSystem = new CachedInputFileSystem(fs, 60000);
|
38
45
|
const inputFileSystem = compiler.inputFileSystem;
|
39
46
|
compiler.outputFileSystem = fs;
|
package/lib/node/nodeConsole.js
CHANGED
@@ -8,127 +8,136 @@
|
|
8
8
|
const util = require("util");
|
9
9
|
const truncateArgs = require("../logging/truncateArgs");
|
10
10
|
|
11
|
-
|
11
|
+
module.exports = ({ colors, appendOnly, stream }) => {
|
12
|
+
let currentStatusMessage = undefined;
|
13
|
+
let hasStatusMessage = false;
|
14
|
+
let currentIndent = "";
|
15
|
+
let currentCollapsed = 0;
|
12
16
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
);
|
28
|
-
} else {
|
29
|
-
return prefix + str.replace(/\n/g, "\n" + prefix);
|
30
|
-
}
|
31
|
-
};
|
17
|
+
const indent = (str, prefix, colorPrefix, colorSuffix) => {
|
18
|
+
if (str === "") return str;
|
19
|
+
prefix = currentIndent + prefix;
|
20
|
+
if (colors) {
|
21
|
+
return (
|
22
|
+
prefix +
|
23
|
+
colorPrefix +
|
24
|
+
str.replace(/\n/g, colorSuffix + "\n" + prefix + colorPrefix) +
|
25
|
+
colorSuffix
|
26
|
+
);
|
27
|
+
} else {
|
28
|
+
return prefix + str.replace(/\n/g, "\n" + prefix);
|
29
|
+
}
|
30
|
+
};
|
32
31
|
|
33
|
-
const clearStatusMessage = () => {
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
};
|
32
|
+
const clearStatusMessage = () => {
|
33
|
+
if (hasStatusMessage) {
|
34
|
+
stream.write("\x1b[2K\r");
|
35
|
+
hasStatusMessage = false;
|
36
|
+
}
|
37
|
+
};
|
39
38
|
|
40
|
-
const writeStatusMessage = () => {
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
};
|
39
|
+
const writeStatusMessage = () => {
|
40
|
+
if (!currentStatusMessage) return;
|
41
|
+
const l = stream.columns;
|
42
|
+
const args = l
|
43
|
+
? truncateArgs(currentStatusMessage, l - 1)
|
44
|
+
: currentStatusMessage;
|
45
|
+
const str = args.join(" ");
|
46
|
+
const coloredStr = `\u001b[1m${str}\u001b[39m\u001b[22m`;
|
47
|
+
stream.write(`\x1b[2K\r${coloredStr}`);
|
48
|
+
hasStatusMessage = true;
|
49
|
+
};
|
51
50
|
|
52
|
-
const writeColored = (prefix, colorPrefix, colorSuffix) => {
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
51
|
+
const writeColored = (prefix, colorPrefix, colorSuffix) => {
|
52
|
+
return (...args) => {
|
53
|
+
if (currentCollapsed > 0) return;
|
54
|
+
clearStatusMessage();
|
55
|
+
const str = indent(
|
56
|
+
util.format(...args),
|
57
|
+
prefix,
|
58
|
+
colorPrefix,
|
59
|
+
colorSuffix
|
60
|
+
);
|
61
|
+
stream.write(str + "\n");
|
62
|
+
writeStatusMessage();
|
63
|
+
};
|
59
64
|
};
|
60
|
-
};
|
61
65
|
|
62
|
-
const writeGroupMessage = writeColored(
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
);
|
66
|
+
const writeGroupMessage = writeColored(
|
67
|
+
"<-> ",
|
68
|
+
"\u001b[1m\u001b[36m",
|
69
|
+
"\u001b[39m\u001b[22m"
|
70
|
+
);
|
67
71
|
|
68
|
-
const writeGroupCollapsedMessage = writeColored(
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
);
|
72
|
+
const writeGroupCollapsedMessage = writeColored(
|
73
|
+
"<+> ",
|
74
|
+
"\u001b[1m\u001b[36m",
|
75
|
+
"\u001b[39m\u001b[22m"
|
76
|
+
);
|
73
77
|
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
78
|
+
return {
|
79
|
+
log: writeColored(" ", "\u001b[1m", "\u001b[22m"),
|
80
|
+
debug: writeColored(" ", "", ""),
|
81
|
+
trace: writeColored(" ", "", ""),
|
82
|
+
info: writeColored("<i> ", "\u001b[1m\u001b[32m", "\u001b[39m\u001b[22m"),
|
83
|
+
warn: writeColored("<w> ", "\u001b[1m\u001b[33m", "\u001b[39m\u001b[22m"),
|
84
|
+
error: writeColored("<e> ", "\u001b[1m\u001b[31m", "\u001b[39m\u001b[22m"),
|
85
|
+
logTime: writeColored(
|
86
|
+
"<t> ",
|
87
|
+
"\u001b[1m\u001b[35m",
|
88
|
+
"\u001b[39m\u001b[22m"
|
89
|
+
),
|
90
|
+
group: (...args) => {
|
91
|
+
writeGroupMessage(...args);
|
92
|
+
if (currentCollapsed > 0) {
|
93
|
+
currentCollapsed++;
|
94
|
+
} else {
|
95
|
+
currentIndent += " ";
|
96
|
+
}
|
97
|
+
},
|
98
|
+
groupCollapsed: (...args) => {
|
99
|
+
writeGroupCollapsedMessage(...args);
|
85
100
|
currentCollapsed++;
|
86
|
-
}
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
currentCollapsed++;
|
93
|
-
},
|
94
|
-
groupEnd: () => {
|
95
|
-
if (currentCollapsed > 0) currentCollapsed--;
|
96
|
-
else if (currentIndent.length >= 2)
|
97
|
-
currentIndent = currentIndent.slice(0, currentIndent.length - 2);
|
98
|
-
},
|
99
|
-
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
100
|
-
profile: console.profile && (name => console.profile(name)),
|
101
|
-
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
102
|
-
profileEnd: console.profileEnd && (name => console.profileEnd(name)),
|
103
|
-
clear:
|
104
|
-
tty &&
|
101
|
+
},
|
102
|
+
groupEnd: () => {
|
103
|
+
if (currentCollapsed > 0) currentCollapsed--;
|
104
|
+
else if (currentIndent.length >= 2)
|
105
|
+
currentIndent = currentIndent.slice(0, currentIndent.length - 2);
|
106
|
+
},
|
105
107
|
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
106
|
-
console.
|
107
|
-
|
108
|
-
|
108
|
+
profile: console.profile && (name => console.profile(name)),
|
109
|
+
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
110
|
+
profileEnd: console.profileEnd && (name => console.profileEnd(name)),
|
111
|
+
clear:
|
112
|
+
!appendOnly &&
|
109
113
|
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
110
|
-
console.clear
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
name.
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
114
|
+
console.clear &&
|
115
|
+
(() => {
|
116
|
+
clearStatusMessage();
|
117
|
+
// eslint-disable-next-line node/no-unsupported-features/node-builtins
|
118
|
+
console.clear();
|
119
|
+
writeStatusMessage();
|
120
|
+
}),
|
121
|
+
status: appendOnly
|
122
|
+
? writeColored("<s> ", "", "")
|
123
|
+
: (name, ...args) => {
|
124
|
+
args = args.filter(Boolean);
|
125
|
+
if (name === undefined && args.length === 0) {
|
126
|
+
clearStatusMessage();
|
127
|
+
currentStatusMessage = undefined;
|
128
|
+
} else if (
|
129
|
+
typeof name === "string" &&
|
130
|
+
name.startsWith("[webpack.Progress] ")
|
131
|
+
) {
|
132
|
+
currentStatusMessage = [name.slice(19), ...args];
|
133
|
+
writeStatusMessage();
|
134
|
+
} else if (name === "[webpack.Progress]") {
|
135
|
+
currentStatusMessage = [...args];
|
136
|
+
writeStatusMessage();
|
137
|
+
} else {
|
138
|
+
currentStatusMessage = [name, ...args];
|
139
|
+
writeStatusMessage();
|
140
|
+
}
|
141
|
+
}
|
142
|
+
};
|
134
143
|
};
|
@@ -253,13 +253,13 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
253
253
|
*/
|
254
254
|
serialize(data, context) {
|
255
255
|
/** @type {any[]} */
|
256
|
-
|
256
|
+
let result = [CURRENT_VERSION];
|
257
257
|
let currentPos = 0;
|
258
|
-
|
258
|
+
let referenceable = new Map();
|
259
259
|
const addReferenceable = item => {
|
260
260
|
referenceable.set(item, currentPos++);
|
261
261
|
};
|
262
|
-
|
262
|
+
let bufferDedupeMap = new Map();
|
263
263
|
const dedupeBuffer = buf => {
|
264
264
|
const len = buf.length;
|
265
265
|
const entry = bufferDedupeMap.get(len);
|
@@ -322,7 +322,7 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
322
322
|
}
|
323
323
|
};
|
324
324
|
let currentPosTypeLookup = 0;
|
325
|
-
|
325
|
+
let objectTypeLookup = new Map();
|
326
326
|
const cycleStack = new Set();
|
327
327
|
const stackToString = item => {
|
328
328
|
const arr = Array.from(cycleStack);
|
@@ -370,7 +370,7 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
370
370
|
.join(" -> ");
|
371
371
|
};
|
372
372
|
let hasDebugInfoAttached;
|
373
|
-
|
373
|
+
let ctx = {
|
374
374
|
write(value, key) {
|
375
375
|
try {
|
376
376
|
process(value);
|
@@ -408,16 +408,13 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
408
408
|
};
|
409
409
|
this.extendContext(ctx);
|
410
410
|
const process = item => {
|
411
|
-
// check if we can emit a reference
|
412
|
-
const ref = referenceable.get(item);
|
413
|
-
|
414
|
-
if (ref !== undefined) {
|
415
|
-
result.push(ESCAPE, ref - currentPos);
|
416
|
-
|
417
|
-
return;
|
418
|
-
}
|
419
|
-
|
420
411
|
if (Buffer.isBuffer(item)) {
|
412
|
+
// check if we can emit a reference
|
413
|
+
const ref = referenceable.get(item);
|
414
|
+
if (ref !== undefined) {
|
415
|
+
result.push(ESCAPE, ref - currentPos);
|
416
|
+
return;
|
417
|
+
}
|
421
418
|
const alreadyUsedBuffer = dedupeBuffer(item);
|
422
419
|
if (alreadyUsedBuffer !== item) {
|
423
420
|
const ref = referenceable.get(alreadyUsedBuffer);
|
@@ -431,7 +428,19 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
431
428
|
addReferenceable(item);
|
432
429
|
|
433
430
|
result.push(item);
|
434
|
-
} else if (
|
431
|
+
} else if (item === ESCAPE) {
|
432
|
+
result.push(ESCAPE, ESCAPE_ESCAPE_VALUE);
|
433
|
+
} else if (
|
434
|
+
typeof item === "object"
|
435
|
+
// We don't have to check for null as ESCAPE is null and this has been checked before
|
436
|
+
) {
|
437
|
+
// check if we can emit a reference
|
438
|
+
const ref = referenceable.get(item);
|
439
|
+
if (ref !== undefined) {
|
440
|
+
result.push(ESCAPE, ref - currentPos);
|
441
|
+
return;
|
442
|
+
}
|
443
|
+
|
435
444
|
if (cycleStack.has(item)) {
|
436
445
|
throw new Error(`Circular references can't be serialized`);
|
437
446
|
}
|
@@ -464,6 +473,12 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
464
473
|
} else if (typeof item === "string") {
|
465
474
|
if (item.length > 1) {
|
466
475
|
// short strings are shorter when not emitting a reference (this saves 1 byte per empty string)
|
476
|
+
// check if we can emit a reference
|
477
|
+
const ref = referenceable.get(item);
|
478
|
+
if (ref !== undefined) {
|
479
|
+
result.push(ESCAPE, ref - currentPos);
|
480
|
+
return;
|
481
|
+
}
|
467
482
|
addReferenceable(item);
|
468
483
|
}
|
469
484
|
|
@@ -476,8 +491,6 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
476
491
|
}
|
477
492
|
|
478
493
|
result.push(item);
|
479
|
-
} else if (item === ESCAPE) {
|
480
|
-
result.push(ESCAPE, ESCAPE_ESCAPE_VALUE);
|
481
494
|
} else if (typeof item === "function") {
|
482
495
|
if (!SerializerMiddleware.isLazy(item))
|
483
496
|
throw new Error("Unexpected function " + item);
|
@@ -511,13 +524,18 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
511
524
|
for (const item of data) {
|
512
525
|
process(item);
|
513
526
|
}
|
527
|
+
return result;
|
514
528
|
} catch (e) {
|
515
529
|
if (e === NOT_SERIALIZABLE) return null;
|
516
530
|
|
517
531
|
throw e;
|
532
|
+
} finally {
|
533
|
+
// Get rid of these references to avoid leaking memory
|
534
|
+
// This happens because the optimized code v8 generates
|
535
|
+
// is optimized for our "ctx.write" method so it will reference
|
536
|
+
// it from e. g. Dependency.prototype.serialize -(IC)-> ctx.write
|
537
|
+
data = result = referenceable = bufferDedupeMap = objectTypeLookup = ctx = undefined;
|
518
538
|
}
|
519
|
-
|
520
|
-
return result;
|
521
539
|
}
|
522
540
|
|
523
541
|
/**
|
@@ -545,8 +563,8 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
545
563
|
};
|
546
564
|
let currentPosTypeLookup = 0;
|
547
565
|
let objectTypeLookup = [];
|
548
|
-
|
549
|
-
|
566
|
+
let result = [];
|
567
|
+
let ctx = {
|
550
568
|
read() {
|
551
569
|
return decodeValue();
|
552
570
|
},
|
@@ -673,16 +691,18 @@ class ObjectMiddleware extends SerializerMiddleware {
|
|
673
691
|
}
|
674
692
|
};
|
675
693
|
|
676
|
-
|
677
|
-
|
694
|
+
try {
|
695
|
+
while (currentDataPos < data.length) {
|
696
|
+
result.push(decodeValue());
|
697
|
+
}
|
698
|
+
return result;
|
699
|
+
} finally {
|
700
|
+
// Get rid of these references to avoid leaking memory
|
701
|
+
// This happens because the optimized code v8 generates
|
702
|
+
// is optimized for our "ctx.read" method so it will reference
|
703
|
+
// it from e. g. Dependency.prototype.deserialize -(IC)-> ctx.read
|
704
|
+
result = referenceable = data = objectTypeLookup = ctx = undefined;
|
678
705
|
}
|
679
|
-
|
680
|
-
// Help the GC, as functions above might be cached in inline caches
|
681
|
-
referenceable = undefined;
|
682
|
-
objectTypeLookup = undefined;
|
683
|
-
data = undefined;
|
684
|
-
|
685
|
-
return result;
|
686
706
|
}
|
687
707
|
}
|
688
708
|
|