@ttsc/playground 0.19.3 → 0.20.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/README.md +6 -0
- package/lib/src/npm/collectExternalPackageNames.js +436 -73
- package/lib/src/npm/collectExternalPackageNames.js.map +1 -1
- package/lib/src/npm/installPlaygroundDependencies.d.ts +5 -3
- package/lib/src/npm/installPlaygroundDependencies.js +230 -27
- package/lib/src/npm/installPlaygroundDependencies.js.map +1 -1
- package/lib/src/npm/internal/npmRegistry.d.ts +13 -2
- package/lib/src/npm/internal/npmRegistry.js +73 -50
- package/lib/src/npm/internal/npmRegistry.js.map +1 -1
- package/lib/src/npm/packageNameFromSpecifier.js +17 -4
- package/lib/src/npm/packageNameFromSpecifier.js.map +1 -1
- package/lib/src/react/PlaygroundShell.js +68 -61
- package/lib/src/react/PlaygroundShell.js.map +1 -1
- package/lib/src/react/createCompilerClient.d.ts +3 -3
- package/lib/src/react/createCompilerClient.js +32 -54
- package/lib/src/react/createCompilerClient.js.map +1 -1
- package/lib/src/sandbox/createSandboxRequire.js +117 -54
- package/lib/src/sandbox/createSandboxRequire.js.map +1 -1
- package/lib/src/structures/IPlaygroundDependencyInstallOptions.d.ts +13 -1
- package/lib/src/structures/IPlaygroundDependencyInstallResult.d.ts +4 -0
- package/lib/src/structures/IPlaygroundDependencyPackage.d.ts +2 -0
- package/lib/src/structures/IPlaygroundDependencyRequest.d.ts +9 -0
- package/lib/src/structures/IPlaygroundDependencyRequest.js +3 -0
- package/lib/src/structures/IPlaygroundDependencyRequest.js.map +1 -0
- package/lib/src/structures/IPlaygroundInstalledDependency.d.ts +12 -0
- package/lib/src/structures/IPlaygroundInstalledDependency.js +3 -0
- package/lib/src/structures/IPlaygroundInstalledDependency.js.map +1 -0
- package/lib/src/structures/index.d.ts +2 -0
- package/lib/src/structures/index.js +2 -0
- package/lib/src/structures/index.js.map +1 -1
- package/package.json +6 -4
- package/src/npm/collectExternalPackageNames.ts +503 -68
- package/src/npm/installPlaygroundDependencies.ts +288 -29
- package/src/npm/internal/npmRegistry.ts +99 -38
- package/src/npm/packageNameFromSpecifier.ts +16 -3
- package/src/react/PlaygroundShell.tsx +86 -72
- package/src/react/createCompilerClient.ts +37 -51
- package/src/sandbox/createSandboxRequire.ts +140 -49
- package/src/structures/IPlaygroundDependencyInstallOptions.ts +13 -1
- package/src/structures/IPlaygroundDependencyInstallResult.ts +4 -0
- package/src/structures/IPlaygroundDependencyPackage.ts +2 -0
- package/src/structures/IPlaygroundDependencyRequest.ts +9 -0
- package/src/structures/IPlaygroundInstalledDependency.ts +13 -0
- package/src/structures/index.ts +2 -0
|
@@ -1,8 +1,4 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
// Internal npm-registry helpers used by `installPlaygroundDependencies`.
|
|
3
|
-
// Grouped in one file because every helper is privately coupled to the tar
|
|
4
|
-
// + version-resolve + tarball-extract flow; splitting them per the public
|
|
5
|
-
// "one symbol per file" rule would make the install path harder to follow.
|
|
6
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
3
|
exports.DECLARATION_FILE_REGEXP = void 0;
|
|
8
4
|
exports.throwIfAborted = throwIfAborted;
|
|
@@ -13,6 +9,7 @@ exports.unpackNpmTarball = unpackNpmTarball;
|
|
|
13
9
|
exports.mountPackageFiles = mountPackageFiles;
|
|
14
10
|
exports.enqueuePackageDependencies = enqueuePackageDependencies;
|
|
15
11
|
exports.toTypesPackageName = toTypesPackageName;
|
|
12
|
+
const semver_1 = require("semver");
|
|
16
13
|
const TEXT_FILE_REGEXP = /(^package\.json$|\.([cm]?js|jsx|[cm]?ts|tsx|json)$|\.d\.[cm]?ts$)/i;
|
|
17
14
|
exports.DECLARATION_FILE_REGEXP = /\.d\.[cm]?ts$/i;
|
|
18
15
|
const RUNTIME_FILE_REGEXP = /(^package\.json$|\.([cm]?js|json)$)/i;
|
|
@@ -37,24 +34,31 @@ async function fetchNpmMetadata(fetchImpl, packageName, optional, signal) {
|
|
|
37
34
|
}
|
|
38
35
|
return (await response.json());
|
|
39
36
|
}
|
|
40
|
-
function selectVersion(metadata,
|
|
37
|
+
function selectVersion(metadata, ranges) {
|
|
41
38
|
const versions = metadata.versions;
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
const
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
39
|
+
const requested = Array.isArray(ranges) ? ranges : [ranges];
|
|
40
|
+
const semverRanges = requested.filter((range) => (0, semver_1.validRange)(range) !== null);
|
|
41
|
+
const tags = requested.filter((range) => (0, semver_1.validRange)(range) === null);
|
|
42
|
+
const taggedVersions = new Set();
|
|
43
|
+
for (const tag of tags) {
|
|
44
|
+
const version = metadata["dist-tags"]?.[tag];
|
|
45
|
+
if (!version || !versions[version]) {
|
|
46
|
+
throw new Error(`No npm dist-tag ${JSON.stringify(tag)} exists for ${metadata.name}.`);
|
|
47
|
+
}
|
|
48
|
+
taggedVersions.add(version);
|
|
49
|
+
}
|
|
50
|
+
if (taggedVersions.size > 1) {
|
|
51
|
+
throw new Error(`Conflicting npm tags for ${metadata.name}: ${requested.join(", ")}.`);
|
|
52
|
+
}
|
|
53
|
+
const candidates = Object.keys(versions).filter((version) => (0, semver_1.valid)(version) !== null &&
|
|
54
|
+
semverRanges.every((range) => (0, semver_1.satisfies)(version, range)) &&
|
|
55
|
+
(taggedVersions.size === 0 || taggedVersions.has(version)));
|
|
56
|
+
const selected = (0, semver_1.maxSatisfying)(candidates, "*");
|
|
57
|
+
if (selected)
|
|
58
|
+
return selected;
|
|
59
|
+
throw new Error(`No version of ${metadata.name} satisfies ${requested
|
|
60
|
+
.map((range) => JSON.stringify(range))
|
|
61
|
+
.join(", ")}.`);
|
|
58
62
|
}
|
|
59
63
|
async function downloadTarball(fetchImpl, tarball, signal) {
|
|
60
64
|
const response = await fetchImpl(tarball, { signal });
|
|
@@ -88,7 +92,7 @@ async function unpackNpmTarball(tgz, signal) {
|
|
|
88
92
|
continue;
|
|
89
93
|
}
|
|
90
94
|
if (type === "x") {
|
|
91
|
-
paxPath = parsePaxPath(
|
|
95
|
+
paxPath = parsePaxPath(body);
|
|
92
96
|
continue;
|
|
93
97
|
}
|
|
94
98
|
if (type !== "0" && type !== "\0") {
|
|
@@ -140,10 +144,15 @@ function mountPackageFiles(packageName, files) {
|
|
|
140
144
|
}
|
|
141
145
|
return { compilerFiles, editorLibs, runtimeFiles };
|
|
142
146
|
}
|
|
143
|
-
function enqueuePackageDependencies(packageJson, enqueue) {
|
|
147
|
+
function enqueuePackageDependencies(packageJson, enqueue, requester) {
|
|
148
|
+
const optionalDependencies = packageJson.optionalDependencies ?? {};
|
|
144
149
|
for (const [name, range] of Object.entries(packageJson.dependencies ?? {})) {
|
|
150
|
+
if (!(name in optionalDependencies) && isRegistryRange(range))
|
|
151
|
+
enqueue({ name, range, optional: false, requester });
|
|
152
|
+
}
|
|
153
|
+
for (const [name, range] of Object.entries(optionalDependencies)) {
|
|
145
154
|
if (isRegistryRange(range))
|
|
146
|
-
enqueue({ name, range, optional:
|
|
155
|
+
enqueue({ name, range, optional: true, requester });
|
|
147
156
|
}
|
|
148
157
|
for (const [name, range] of Object.entries(packageJson.peerDependencies ?? {})) {
|
|
149
158
|
const optional = packageJson.peerDependenciesMeta?.[name]?.optional === true;
|
|
@@ -153,11 +162,25 @@ function enqueuePackageDependencies(packageJson, enqueue) {
|
|
|
153
162
|
// silent skip that leaves the wasm-side compile reporting a generic
|
|
154
163
|
// "Cannot find module" with no breadcrumb back to the dep installer.
|
|
155
164
|
if (!optional && isRegistryRange(range))
|
|
156
|
-
enqueue({ name, range, optional: false });
|
|
165
|
+
enqueue({ name, range, optional: false, requester });
|
|
157
166
|
}
|
|
158
167
|
}
|
|
159
168
|
function isRegistryRange(range) {
|
|
160
|
-
|
|
169
|
+
const spec = range.trim();
|
|
170
|
+
// Match npm-package-arg's file classification before its registry fallback:
|
|
171
|
+
// dot/home/root/drive paths and tar archive names are source specs even
|
|
172
|
+
// though their characters could also form a URI-safe dist-tag.
|
|
173
|
+
if (/^(?:\.|~[\\/]|[\\/]|[a-zA-Z]:)/.test(spec) ||
|
|
174
|
+
/\.(?:tgz|tar\.gz|tar)$/i.test(spec))
|
|
175
|
+
return false;
|
|
176
|
+
if (spec.startsWith("npm:"))
|
|
177
|
+
return true;
|
|
178
|
+
if ((0, semver_1.validRange)(spec) !== null)
|
|
179
|
+
return true;
|
|
180
|
+
// npm accepts a dist-tag only when it is a non-empty URI-component-safe
|
|
181
|
+
// token. Git, hosted, URL, and local-path specs all require punctuation that
|
|
182
|
+
// encodeURIComponent escapes, so they cannot fall through as fake tags.
|
|
183
|
+
return spec.length > 0 && encodeURIComponent(spec) === spec;
|
|
161
184
|
}
|
|
162
185
|
function toTypesPackageName(packageName) {
|
|
163
186
|
if (!packageName.startsWith("@"))
|
|
@@ -176,22 +199,33 @@ function parseOctal(bytes) {
|
|
|
176
199
|
const text = trimNull(new TextDecoder().decode(bytes)).trim();
|
|
177
200
|
return text ? Number.parseInt(text, 8) : 0;
|
|
178
201
|
}
|
|
179
|
-
function parsePaxPath(
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
202
|
+
function parsePaxPath(bytes) {
|
|
203
|
+
const decoder = new TextDecoder();
|
|
204
|
+
let offset = 0;
|
|
205
|
+
let path = null;
|
|
206
|
+
while (offset < bytes.length) {
|
|
207
|
+
let space = offset;
|
|
208
|
+
while (space < bytes.length && bytes[space] !== 0x20)
|
|
209
|
+
space++;
|
|
210
|
+
if (space === bytes.length)
|
|
211
|
+
throw new Error("Invalid PAX header length.");
|
|
212
|
+
const lengthText = decoder.decode(bytes.subarray(offset, space));
|
|
213
|
+
if (!/^[1-9][0-9]*$/.test(lengthText))
|
|
214
|
+
throw new Error("Invalid PAX header length.");
|
|
215
|
+
const length = Number(lengthText);
|
|
216
|
+
const end = offset + length;
|
|
217
|
+
if (!Number.isSafeInteger(length) ||
|
|
218
|
+
length <= space - offset + 1 ||
|
|
219
|
+
end > bytes.length ||
|
|
220
|
+
bytes[end - 1] !== 0x0a)
|
|
221
|
+
throw new Error("Invalid PAX header record.");
|
|
222
|
+
const record = decoder.decode(bytes.subarray(space + 1, end - 1));
|
|
189
223
|
const eq = record.indexOf("=");
|
|
190
224
|
if (eq > 0 && record.slice(0, eq) === "path")
|
|
191
|
-
|
|
192
|
-
|
|
225
|
+
path = record.slice(eq + 1);
|
|
226
|
+
offset = end;
|
|
193
227
|
}
|
|
194
|
-
return
|
|
228
|
+
return path;
|
|
195
229
|
}
|
|
196
230
|
function stripTarRoot(path) {
|
|
197
231
|
const normalized = path.replace(/\\/g, "/").replace(/^\/+/, "");
|
|
@@ -202,15 +236,4 @@ function stripTarRoot(path) {
|
|
|
202
236
|
const slash = normalized.indexOf("/");
|
|
203
237
|
return slash < 0 ? normalized : normalized.slice(slash + 1);
|
|
204
238
|
}
|
|
205
|
-
function compareVersionDesc(a, b) {
|
|
206
|
-
const pa = a.split(/[.-]/).map((part) => Number.parseInt(part, 10));
|
|
207
|
-
const pb = b.split(/[.-]/).map((part) => Number.parseInt(part, 10));
|
|
208
|
-
for (let i = 0; i < Math.max(pa.length, pb.length); i++) {
|
|
209
|
-
const av = Number.isFinite(pa[i]) ? pa[i] : 0;
|
|
210
|
-
const bv = Number.isFinite(pb[i]) ? pb[i] : 0;
|
|
211
|
-
if (av !== bv)
|
|
212
|
-
return bv - av;
|
|
213
|
-
}
|
|
214
|
-
return b.localeCompare(a);
|
|
215
|
-
}
|
|
216
239
|
//# sourceMappingURL=npmRegistry.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"npmRegistry.js","sourceRoot":"","sources":["../../../../src/npm/internal/npmRegistry.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"npmRegistry.js","sourceRoot":"","sources":["../../../../src/npm/internal/npmRegistry.ts"],"names":[],"mappings":"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"}
|
|
@@ -3,16 +3,23 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.packageNameFromSpecifier = packageNameFromSpecifier;
|
|
4
4
|
const BUILTIN_MODULES = new Set([
|
|
5
5
|
"assert",
|
|
6
|
+
"async_hooks",
|
|
6
7
|
"buffer",
|
|
7
8
|
"child_process",
|
|
9
|
+
"cluster",
|
|
8
10
|
"console",
|
|
9
11
|
"constants",
|
|
10
12
|
"crypto",
|
|
13
|
+
"dgram",
|
|
14
|
+
"diagnostics_channel",
|
|
11
15
|
"dns",
|
|
16
|
+
"domain",
|
|
12
17
|
"events",
|
|
13
18
|
"fs",
|
|
14
19
|
"http",
|
|
20
|
+
"http2",
|
|
15
21
|
"https",
|
|
22
|
+
"inspector",
|
|
16
23
|
"module",
|
|
17
24
|
"net",
|
|
18
25
|
"os",
|
|
@@ -22,14 +29,19 @@ const BUILTIN_MODULES = new Set([
|
|
|
22
29
|
"punycode",
|
|
23
30
|
"querystring",
|
|
24
31
|
"readline",
|
|
32
|
+
"repl",
|
|
25
33
|
"stream",
|
|
26
34
|
"string_decoder",
|
|
35
|
+
"sys",
|
|
27
36
|
"timers",
|
|
28
37
|
"tls",
|
|
38
|
+
"trace_events",
|
|
29
39
|
"tty",
|
|
30
40
|
"url",
|
|
31
41
|
"util",
|
|
42
|
+
"v8",
|
|
32
43
|
"vm",
|
|
44
|
+
"wasi",
|
|
33
45
|
"worker_threads",
|
|
34
46
|
"zlib",
|
|
35
47
|
]);
|
|
@@ -40,15 +52,16 @@ const BUILTIN_MODULES = new Set([
|
|
|
40
52
|
* built-in modules — the caller doesn't install those from npm.
|
|
41
53
|
*/
|
|
42
54
|
function packageNameFromSpecifier(specifier) {
|
|
55
|
+
const nodePrefixed = specifier.startsWith("node:");
|
|
56
|
+
const bare = nodePrefixed ? specifier.slice("node:".length) : specifier;
|
|
57
|
+
const first = bare.split("/")[0];
|
|
58
|
+
if (first && BUILTIN_MODULES.has(first))
|
|
59
|
+
return null;
|
|
43
60
|
if (specifier.startsWith("#") ||
|
|
44
61
|
specifier.startsWith(".") ||
|
|
45
62
|
specifier.startsWith("/") ||
|
|
46
63
|
/^[a-z][a-z0-9+.-]*:/i.test(specifier))
|
|
47
64
|
return null;
|
|
48
|
-
const bare = specifier.startsWith("node:") ? specifier.slice(5) : specifier;
|
|
49
|
-
const first = bare.split("/")[0];
|
|
50
|
-
if (first && BUILTIN_MODULES.has(first))
|
|
51
|
-
return null;
|
|
52
65
|
if (bare.startsWith("@")) {
|
|
53
66
|
const firstSlash = bare.indexOf("/");
|
|
54
67
|
if (firstSlash < 0)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"packageNameFromSpecifier.js","sourceRoot":"","sources":["../../../src/npm/packageNameFromSpecifier.ts"],"names":[],"mappings":";;;AAAA,MAAM,eAAe,GAAG,IAAI,GAAG,CAAC;IAC9B,QAAQ;IACR,QAAQ;IACR,eAAe;IACf,SAAS;IACT,WAAW;IACX,QAAQ;IACR,KAAK;IACL,QAAQ;IACR,IAAI;IACJ,MAAM;IACN,OAAO;IACP,QAAQ;IACR,KAAK;IACL,IAAI;IACJ,MAAM;IACN,YAAY;IACZ,SAAS;IACT,UAAU;IACV,aAAa;IACb,UAAU;IACV,QAAQ;IACR,gBAAgB;IAChB,QAAQ;IACR,KAAK;IACL,KAAK;IACL,KAAK;IACL,MAAM;IACN,IAAI;IACJ,gBAAgB;IAChB,MAAM;CACP,CAAC,CAAC;AAEH;;;;;GAKG;AACH,kCAAyC,SAAiB;IACxD,
|
|
1
|
+
{"version":3,"file":"packageNameFromSpecifier.js","sourceRoot":"","sources":["../../../src/npm/packageNameFromSpecifier.ts"],"names":[],"mappings":";;;AAAA,MAAM,eAAe,GAAG,IAAI,GAAG,CAAC;IAC9B,QAAQ;IACR,aAAa;IACb,QAAQ;IACR,eAAe;IACf,SAAS;IACT,SAAS;IACT,WAAW;IACX,QAAQ;IACR,OAAO;IACP,qBAAqB;IACrB,KAAK;IACL,QAAQ;IACR,QAAQ;IACR,IAAI;IACJ,MAAM;IACN,OAAO;IACP,OAAO;IACP,WAAW;IACX,QAAQ;IACR,KAAK;IACL,IAAI;IACJ,MAAM;IACN,YAAY;IACZ,SAAS;IACT,UAAU;IACV,aAAa;IACb,UAAU;IACV,MAAM;IACN,QAAQ;IACR,gBAAgB;IAChB,KAAK;IACL,QAAQ;IACR,KAAK;IACL,cAAc;IACd,KAAK;IACL,KAAK;IACL,MAAM;IACN,IAAI;IACJ,IAAI;IACJ,MAAM;IACN,gBAAgB;IAChB,MAAM;CACP,CAAC,CAAC;AAEH;;;;;GAKG;AACH,kCAAyC,SAAiB;IACxD,MAAM,YAAY,GAAG,SAAS,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC;IACnD,MAAM,IAAI,GAAG,YAAY,CAAC,CAAC,CAAC,SAAS,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;IACxE,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;IACjC,IAAI,KAAK,IAAI,eAAe,CAAC,GAAG,CAAC,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IACrD,IACE,SAAS,CAAC,UAAU,CAAC,GAAG,CAAC;QACzB,SAAS,CAAC,UAAU,CAAC,GAAG,CAAC;QACzB,SAAS,CAAC,UAAU,CAAC,GAAG,CAAC;QACzB,sBAAsB,CAAC,IAAI,CAAC,SAAS,CAAC;QAEtC,OAAO,IAAI,CAAC;IACd,IAAI,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,EAAE,CAAC;QACzB,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;QACrC,IAAI,UAAU,GAAG,CAAC;YAAE,OAAO,IAAI,CAAC;QAChC,IAAI,UAAU,KAAK,CAAC;YAAE,OAAO,IAAI,CAAC;QAClC,MAAM,WAAW,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,EAAE,UAAU,GAAG,CAAC,CAAC,CAAC;QACtD,IAAI,WAAW,KAAK,UAAU,GAAG,CAAC;YAAE,OAAO,IAAI,CAAC;QAChD,OAAO,WAAW,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,WAAW,CAAC,CAAC;IAC7D,CAAC;IACD,MAAM,KAAK,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAChC,OAAO,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,KAAK,CAAC,CAAC;AACjD,CAAC"}
|
|
@@ -50,17 +50,12 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
50
50
|
const dependencyProgressTimer = (0, react_1.useRef)(null);
|
|
51
51
|
const dependencyInstallChain = (0, react_1.useRef)(Promise.resolve());
|
|
52
52
|
const dependencyAbort = (0, react_1.useRef)(null);
|
|
53
|
-
//
|
|
54
|
-
//
|
|
55
|
-
|
|
56
|
-
//
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
// (via `preinstalledPackages`) plus everything `installPlaygroundDependencies`
|
|
60
|
-
// has added across the session. A useEffect below merges fresh
|
|
61
|
-
// preinstalledPackages prop values into the ref so a parent that swaps
|
|
62
|
-
// the prop later does not race a now-stale Set.
|
|
63
|
-
const installedDependencyNames = (0, react_1.useRef)(new Set(preinstalledPackages));
|
|
53
|
+
// Exact mounted identities and active requests. A name-only set cannot
|
|
54
|
+
// validate a later transitive range or distinguish an npm alias target.
|
|
55
|
+
const installedDependencies = (0, react_1.useRef)(new Map());
|
|
56
|
+
// Direct source roots selecting the mounted graph. Removing one requires a
|
|
57
|
+
// full solve and worker replacement so obsolete package files cannot survive.
|
|
58
|
+
const dependencyRoots = (0, react_1.useRef)(new Set());
|
|
64
59
|
// Accumulated runtime-file map produced by every successful
|
|
65
60
|
// installPlaygroundDependencies call. Threaded through to executeBundle so
|
|
66
61
|
// the in-page Execute sandbox's require can resolve any npm package the
|
|
@@ -100,16 +95,6 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
100
95
|
setDependencyPackageNames([]);
|
|
101
96
|
setSource(next);
|
|
102
97
|
}, []);
|
|
103
|
-
// ── Sync installedDependencyNames + preinstalledPackagesRef on prop change ──
|
|
104
|
-
// The refs capture the initial value on mount; without this effect a
|
|
105
|
-
// parent that swaps `preinstalledPackages` later would race a stale
|
|
106
|
-
// Set against the fresh prop used in `ignoredPackages` below.
|
|
107
|
-
(0, react_1.useEffect)(() => {
|
|
108
|
-
preinstalledPackagesRef.current = preinstalledPackages;
|
|
109
|
-
for (const name of preinstalledPackages) {
|
|
110
|
-
installedDependencyNames.current.add(name);
|
|
111
|
-
}
|
|
112
|
-
}, [preinstalledPackages]);
|
|
113
98
|
// ── Decode source from URL on mount ──
|
|
114
99
|
(0, react_1.useEffect)(() => {
|
|
115
100
|
const params = new URLSearchParams(window.location.search);
|
|
@@ -142,34 +127,48 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
142
127
|
const installDependenciesForSource = (0, react_1.useCallback)(async (input, version = sourceVersion.current) => {
|
|
143
128
|
const task = dependencyInstallChain.current.then(async () => {
|
|
144
129
|
const firstPassPackageNames = (0, collectExternalPackageNames_1.collectExternalPackageNames)(input, preinstalledPackages);
|
|
145
|
-
|
|
146
|
-
|
|
130
|
+
if (dependencyRootDelta(firstPassPackageNames, dependencyRoots.current)
|
|
131
|
+
.changed === false)
|
|
147
132
|
return null;
|
|
148
133
|
await wait(DEPENDENCY_INSTALL_QUIET_MS);
|
|
149
134
|
if (sourceVersion.current !== version)
|
|
150
135
|
return null;
|
|
151
136
|
const packageNames = (0, collectExternalPackageNames_1.collectExternalPackageNames)(latestSource.current, preinstalledPackages);
|
|
152
|
-
const
|
|
153
|
-
if (
|
|
137
|
+
const delta = dependencyRootDelta(packageNames, dependencyRoots.current);
|
|
138
|
+
if (!delta.changed)
|
|
154
139
|
return null;
|
|
140
|
+
const replacing = delta.removed.length !== 0;
|
|
141
|
+
const requested = replacing ? packageNames : delta.added;
|
|
155
142
|
if (dependencyProgressTimer.current !== null) {
|
|
156
143
|
window.clearTimeout(dependencyProgressTimer.current);
|
|
157
144
|
dependencyProgressTimer.current = null;
|
|
158
145
|
}
|
|
159
|
-
setDependencyPackageNames(
|
|
146
|
+
setDependencyPackageNames(requested);
|
|
160
147
|
const abort = new AbortController();
|
|
161
148
|
dependencyAbort.current = abort;
|
|
149
|
+
let workerMutated = false;
|
|
162
150
|
try {
|
|
163
|
-
const installed = await (0, installPlaygroundDependencies_1.installPlaygroundDependencies)(
|
|
164
|
-
|
|
151
|
+
const installed = await (0, installPlaygroundDependencies_1.installPlaygroundDependencies)(requested, {
|
|
152
|
+
installedDependencies: replacing
|
|
153
|
+
? []
|
|
154
|
+
: installedDependencies.current.values(),
|
|
165
155
|
ignoredPackages: preinstalledPackages,
|
|
166
156
|
signal: abort.signal,
|
|
167
157
|
onProgress: setDependencyProgress,
|
|
168
158
|
});
|
|
169
159
|
if (sourceVersion.current !== version)
|
|
170
160
|
return null;
|
|
161
|
+
if (replacing) {
|
|
162
|
+
workerMutated = true;
|
|
163
|
+
await client.reset();
|
|
164
|
+
installedDependencies.current = new Map();
|
|
165
|
+
dependencyRoots.current = new Set();
|
|
166
|
+
runtimeDependencyFiles.current = {};
|
|
167
|
+
setEditorExtraLibs({});
|
|
168
|
+
}
|
|
171
169
|
if (Object.keys(installed.compilerFiles).length > 0) {
|
|
172
170
|
const service = await createCompilerService();
|
|
171
|
+
workerMutated = true;
|
|
173
172
|
await service.installDependencies({
|
|
174
173
|
files: installed.compilerFiles,
|
|
175
174
|
packages: installed.packages.map(({ name, version }) => ({
|
|
@@ -178,21 +177,17 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
178
177
|
})),
|
|
179
178
|
});
|
|
180
179
|
}
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
runtimeDependencyFiles.current = {
|
|
193
|
-
...runtimeDependencyFiles.current,
|
|
194
|
-
...installed.runtimeFiles,
|
|
195
|
-
};
|
|
180
|
+
installedDependencies.current = new Map(installed.resolvedDependencies.map((dependency) => [dependency.name, dependency]));
|
|
181
|
+
dependencyRoots.current = new Set(packageNames);
|
|
182
|
+
setEditorExtraLibs((previous) => replacing
|
|
183
|
+
? installed.editorLibs
|
|
184
|
+
: { ...previous, ...installed.editorLibs });
|
|
185
|
+
runtimeDependencyFiles.current = replacing
|
|
186
|
+
? installed.runtimeFiles
|
|
187
|
+
: {
|
|
188
|
+
...runtimeDependencyFiles.current,
|
|
189
|
+
...installed.runtimeFiles,
|
|
190
|
+
};
|
|
196
191
|
dependencyProgressTimer.current = window.setTimeout(() => {
|
|
197
192
|
setDependencyProgress(null);
|
|
198
193
|
setDependencyPackageNames([]);
|
|
@@ -201,6 +196,13 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
201
196
|
return null;
|
|
202
197
|
}
|
|
203
198
|
catch (error) {
|
|
199
|
+
if (workerMutated) {
|
|
200
|
+
await client.reset();
|
|
201
|
+
installedDependencies.current = new Map();
|
|
202
|
+
dependencyRoots.current = new Set();
|
|
203
|
+
runtimeDependencyFiles.current = {};
|
|
204
|
+
setEditorExtraLibs({});
|
|
205
|
+
}
|
|
204
206
|
if (isAbortError(error)) {
|
|
205
207
|
setDependencyProgress(null);
|
|
206
208
|
setDependencyPackageNames([]);
|
|
@@ -208,9 +210,9 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
208
210
|
}
|
|
209
211
|
setDependencyProgress({
|
|
210
212
|
phase: "error",
|
|
211
|
-
packageName:
|
|
213
|
+
packageName: requested[0],
|
|
212
214
|
completed: 0,
|
|
213
|
-
total:
|
|
215
|
+
total: requested.length,
|
|
214
216
|
message: describeUnknownError(error),
|
|
215
217
|
});
|
|
216
218
|
dependencyProgressTimer.current = window.setTimeout(() => {
|
|
@@ -227,7 +229,7 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
227
229
|
});
|
|
228
230
|
dependencyInstallChain.current = task.then(() => { });
|
|
229
231
|
return task;
|
|
230
|
-
}, [createCompilerService, preinstalledPackages]);
|
|
232
|
+
}, [client, createCompilerService, preinstalledPackages]);
|
|
231
233
|
// ── Run compile when source / options change ──
|
|
232
234
|
//
|
|
233
235
|
// `target` (the active tab) is intentionally NOT a trigger here: the
|
|
@@ -346,22 +348,17 @@ function PlaygroundShell({ workerUrl, defaultScript, examples = [], exampleGroup
|
|
|
346
348
|
// from the playground leaks one Worker per mount; a workerUrl swap
|
|
347
349
|
// leaks the previous Worker forever.
|
|
348
350
|
//
|
|
349
|
-
// Reset the dependency
|
|
350
|
-
//
|
|
351
|
-
// only `preinstalledPackages` mounted, so carrying the old names
|
|
352
|
-
// would make installDependenciesForSource skip the install (because
|
|
353
|
-
// `installedDependencyNames.current.has(name)` is still true) and
|
|
354
|
-
// the next compile would fail with `Cannot find module`.
|
|
351
|
+
// Reset the dependency graph too. Its exact versions, requests, roots, and
|
|
352
|
+
// runtime files describe only the worker generation that is being closed.
|
|
355
353
|
//
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
runtimeDependencyFiles.current = {};
|
|
354
|
+
(0, react_1.useEffect)(() => {
|
|
355
|
+
setEditorExtraLibs({});
|
|
356
|
+
return () => {
|
|
357
|
+
void client.reset();
|
|
358
|
+
installedDependencies.current = new Map();
|
|
359
|
+
dependencyRoots.current = new Set();
|
|
360
|
+
runtimeDependencyFiles.current = {};
|
|
361
|
+
};
|
|
365
362
|
}, [client]);
|
|
366
363
|
const onPickExample = (0, react_1.useCallback)((id) => {
|
|
367
364
|
const example = examples.find((e) => e.id === id);
|
|
@@ -599,6 +596,16 @@ function normalizeClientError(error) {
|
|
|
599
596
|
function wait(ms) {
|
|
600
597
|
return new Promise((resolve) => window.setTimeout(resolve, ms));
|
|
601
598
|
}
|
|
599
|
+
function dependencyRootDelta(current, previous) {
|
|
600
|
+
const next = new Set(current);
|
|
601
|
+
const added = current.filter((name) => !previous.has(name));
|
|
602
|
+
const removed = [...previous].filter((name) => !next.has(name));
|
|
603
|
+
return {
|
|
604
|
+
added,
|
|
605
|
+
changed: added.length !== 0 || removed.length !== 0,
|
|
606
|
+
removed,
|
|
607
|
+
};
|
|
608
|
+
}
|
|
602
609
|
function createAbortError(reason) {
|
|
603
610
|
const error = new Error(`Dependency install aborted: ${reason}.`);
|
|
604
611
|
error.name = "AbortError";
|