@vendure/cloud-config 0.0.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 +298 -0
- package/dist/cloud-config.d.ts +55 -0
- package/dist/cloud-config.d.ts.map +1 -0
- package/dist/cloud-config.js +2 -0
- package/dist/cloud-config.js.map +1 -0
- package/dist/cloud-dashboard-plugin.d.ts +28 -0
- package/dist/cloud-dashboard-plugin.d.ts.map +1 -0
- package/dist/cloud-dashboard-plugin.js +91 -0
- package/dist/cloud-dashboard-plugin.js.map +1 -0
- package/dist/cloud-plugin-declaration.d.ts +12 -0
- package/dist/cloud-plugin-declaration.d.ts.map +1 -0
- package/dist/cloud-plugin-declaration.js +53 -0
- package/dist/cloud-plugin-declaration.js.map +1 -0
- package/dist/composition.d.ts +23 -0
- package/dist/composition.d.ts.map +1 -0
- package/dist/composition.js +147 -0
- package/dist/composition.js.map +1 -0
- package/dist/define-cloud-config.d.ts +19 -0
- package/dist/define-cloud-config.d.ts.map +1 -0
- package/dist/define-cloud-config.js +47 -0
- package/dist/define-cloud-config.js.map +1 -0
- package/dist/errors.d.ts +4 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +13 -0
- package/dist/errors.js.map +1 -0
- package/dist/index.d.ts +15 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +14 -0
- package/dist/index.js.map +1 -0
- package/dist/migrations.d.ts +32 -0
- package/dist/migrations.d.ts.map +1 -0
- package/dist/migrations.js +250 -0
- package/dist/migrations.js.map +1 -0
- package/dist/outbound-hosts.d.ts +16 -0
- package/dist/outbound-hosts.d.ts.map +1 -0
- package/dist/outbound-hosts.js +211 -0
- package/dist/outbound-hosts.js.map +1 -0
- package/dist/path.d.ts +2 -0
- package/dist/path.d.ts.map +1 -0
- package/dist/path.js +18 -0
- package/dist/path.js.map +1 -0
- package/dist/platform-fields.d.ts +71 -0
- package/dist/platform-fields.d.ts.map +1 -0
- package/dist/platform-fields.js +94 -0
- package/dist/platform-fields.js.map +1 -0
- package/dist/plugin-attribution.d.ts +27 -0
- package/dist/plugin-attribution.d.ts.map +1 -0
- package/dist/plugin-attribution.js +97 -0
- package/dist/plugin-attribution.js.map +1 -0
- package/dist/runtime-backstop.d.ts +8 -0
- package/dist/runtime-backstop.d.ts.map +1 -0
- package/dist/runtime-backstop.js +20 -0
- package/dist/runtime-backstop.js.map +1 -0
- package/dist/secrets.d.ts +14 -0
- package/dist/secrets.d.ts.map +1 -0
- package/dist/secrets.js +109 -0
- package/dist/secrets.js.map +1 -0
- package/dist/stack.d.ts +3 -0
- package/dist/stack.d.ts.map +1 -0
- package/dist/stack.js +58 -0
- package/dist/stack.js.map +1 -0
- package/dist/superseded-plugins.d.ts +19 -0
- package/dist/superseded-plugins.d.ts.map +1 -0
- package/dist/superseded-plugins.js +41 -0
- package/dist/superseded-plugins.js.map +1 -0
- package/dist/vendure-extension.d.ts +38 -0
- package/dist/vendure-extension.d.ts.map +1 -0
- package/dist/vendure-extension.js +111 -0
- package/dist/vendure-extension.js.map +1 -0
- package/package.json +64 -0
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { CloudConfigError } from "./errors.js";
|
|
2
|
+
type LiteralOnly<T extends string> = T & (string extends T ? never : unknown);
|
|
3
|
+
export declare function secret<T extends string>(name: LiteralOnly<T>): string;
|
|
4
|
+
export declare function listDeclaredSecrets(): string[];
|
|
5
|
+
export declare function listMissingSecrets(): string[];
|
|
6
|
+
export declare class MissingSecretsError extends CloudConfigError {
|
|
7
|
+
readonly names: readonly string[];
|
|
8
|
+
constructor(names: readonly string[]);
|
|
9
|
+
}
|
|
10
|
+
export declare function assertNoMissingSecrets(): void;
|
|
11
|
+
export declare function redactSecrets(text: string): string;
|
|
12
|
+
export declare function resetSecretsForTesting(): void;
|
|
13
|
+
export {};
|
|
14
|
+
//# sourceMappingURL=secrets.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"secrets.d.ts","sourceRoot":"","sources":["../src/secrets.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AA8B/C,KAAK,WAAW,CAAC,CAAC,SAAS,MAAM,IAAI,CAAC,GAAG,CAAC,MAAM,SAAS,CAAC,GAAG,KAAK,GAAG,OAAO,CAAC,CAAC;AAgB9E,wBAAgB,MAAM,CAAC,CAAC,SAAS,MAAM,EAAE,IAAI,EAAE,WAAW,CAAC,CAAC,CAAC,GAAG,MAAM,CAuBrE;AAID,wBAAgB,mBAAmB,IAAI,MAAM,EAAE,CAE9C;AAID,wBAAgB,kBAAkB,IAAI,MAAM,EAAE,CAI7C;AAED,qBAAa,mBAAoB,SAAQ,gBAAgB;IACvD,QAAQ,CAAC,KAAK,EAAE,SAAS,MAAM,EAAE,CAAC;gBAEtB,KAAK,EAAE,SAAS,MAAM,EAAE;CAWrC;AAED,wBAAgB,sBAAsB,IAAI,IAAI,CAG7C;AAWD,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CASlD;AAMD,wBAAgB,sBAAsB,IAAI,IAAI,CAE7C"}
|
package/dist/secrets.js
ADDED
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
import { CloudConfigError } from "./errors.js";
|
|
2
|
+
// Registered for the same reason the config handle's symbol is (ADR-0043, ADR-0045): a second
|
|
3
|
+
// copy of this package in the tree would otherwise keep a second registry, and the entrypoint
|
|
4
|
+
// would read a declared set missing whatever the other copy resolved. The peer dependency
|
|
5
|
+
// makes two copies hard to arrive at; this makes them survivable.
|
|
6
|
+
const REGISTRY = Symbol.for("vendure-cloud.secret-registry");
|
|
7
|
+
function registry() {
|
|
8
|
+
const global = globalThis;
|
|
9
|
+
const existing = global[REGISTRY];
|
|
10
|
+
if (existing !== undefined)
|
|
11
|
+
return existing;
|
|
12
|
+
const created = { declared: new Map() };
|
|
13
|
+
global[REGISTRY] = created;
|
|
14
|
+
return created;
|
|
15
|
+
}
|
|
16
|
+
// Reads a customer-supplied value, registers the name, and returns a plain string.
|
|
17
|
+
//
|
|
18
|
+
// Values arrive as ordinary environment variables (ADR-0030): the ECS task execution role
|
|
19
|
+
// fetches the environment's Secrets Manager document at task start, so by the time this runs
|
|
20
|
+
// there is nothing to fetch and nothing asynchronous to wait for. This is a read helper over
|
|
21
|
+
// `process.env`, not a second delivery mechanism.
|
|
22
|
+
//
|
|
23
|
+
// Resolving eagerly and returning a plain string rather than a lazy reference is what keeps
|
|
24
|
+
// third-party plugin options typed `string` working. A wrapper type would leak into every
|
|
25
|
+
// option signature that ever holds a secret.
|
|
26
|
+
//
|
|
27
|
+
// A missing name is recorded rather than thrown here, so that `defineCloudConfig` can fail
|
|
28
|
+
// once naming all of them. Throwing on the first would make a configuration with four unset
|
|
29
|
+
// secrets take four deploys to fix.
|
|
30
|
+
export function secret(name) {
|
|
31
|
+
// Trimmed before anything else looks at it, so that what is tested for emptiness, what is
|
|
32
|
+
// registered for redaction, and what the caller receives are all the same string.
|
|
33
|
+
//
|
|
34
|
+
// The value that arrives is whatever the environment holds, and a credential picks up
|
|
35
|
+
// surrounding whitespace easily — a trailing newline out of a file-based secret store or a
|
|
36
|
+
// `.env` loader is the usual way. That corrupted value fails in the same place an empty one
|
|
37
|
+
// would, inside a payment call rather than at boot, which is the failure this helper exists
|
|
38
|
+
// to move earlier. Treating " " as unset while handing back " sk-live-123\n" intact would
|
|
39
|
+
// catch the rarer half of that and miss the common half.
|
|
40
|
+
//
|
|
41
|
+
// Only the ends are affected. A multi-line value keeps its interior exactly — ADR-0030 notes
|
|
42
|
+
// that customers routinely put private keys and service-account JSON in these variables, and
|
|
43
|
+
// a PEM body survives this untouched.
|
|
44
|
+
const value = process.env[name]?.trim();
|
|
45
|
+
if (value === undefined || value === "") {
|
|
46
|
+
registry().declared.set(name, undefined);
|
|
47
|
+
// The boot fails before anything reads this, so the value is never used. It is a string
|
|
48
|
+
// so that the signature does not have to admit undefined for every caller.
|
|
49
|
+
return "";
|
|
50
|
+
}
|
|
51
|
+
registry().declared.set(name, value);
|
|
52
|
+
return value;
|
|
53
|
+
}
|
|
54
|
+
// The entrypoint's accessor, after composition. Exactly the names passed to `secret()`,
|
|
55
|
+
// whether or not each one resolved, in the order they were passed.
|
|
56
|
+
export function listDeclaredSecrets() {
|
|
57
|
+
return [...registry().declared.keys()];
|
|
58
|
+
}
|
|
59
|
+
// The names that were asked for and are not set. CLO-417 reports these against an
|
|
60
|
+
// environment; `defineCloudConfig` refuses to boot on them.
|
|
61
|
+
export function listMissingSecrets() {
|
|
62
|
+
return [...registry().declared]
|
|
63
|
+
.filter(([, value]) => value === undefined)
|
|
64
|
+
.map(([name]) => name);
|
|
65
|
+
}
|
|
66
|
+
export class MissingSecretsError extends CloudConfigError {
|
|
67
|
+
names;
|
|
68
|
+
constructor(names) {
|
|
69
|
+
const list = names.map((name) => ` - ${name}`).join("\n");
|
|
70
|
+
const one = names.length === 1;
|
|
71
|
+
const secrets = one ? "secret" : "secrets";
|
|
72
|
+
const isAre = one ? "is" : "are";
|
|
73
|
+
const itThem = one ? "it" : "them";
|
|
74
|
+
super(`Vendure Cloud: this configuration reads ${names.length} ${secrets} that ${isAre} not set on this environment.\n\n${list}\n\n Set ${itThem} with \`vcloud env set <NAME> <value>\` and deploy again.\n A value that is set but empty or surrounded by whitespace counts as unset.\n`);
|
|
75
|
+
this.names = names;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
export function assertNoMissingSecrets() {
|
|
79
|
+
const missing = listMissingSecrets();
|
|
80
|
+
if (missing.length > 0)
|
|
81
|
+
throw new MissingSecretsError(missing);
|
|
82
|
+
}
|
|
83
|
+
// Replaces every resolved secret value wherever it appears in a string. The platform logger
|
|
84
|
+
// runs its output through this, which is the hook `process.env` gives no equivalent of: a
|
|
85
|
+
// value read straight out of `process.env` is an ordinary string that nothing can recognise
|
|
86
|
+
// once it reaches a log line.
|
|
87
|
+
//
|
|
88
|
+
// Longest first, so a secret that contains another secret is replaced whole rather than
|
|
89
|
+
// leaving the shorter one's placeholder embedded in it. `split`/`join` rather than a regular
|
|
90
|
+
// expression, because a secret can contain any character and escaping it is one more thing to
|
|
91
|
+
// get wrong.
|
|
92
|
+
export function redactSecrets(text) {
|
|
93
|
+
const values = [...registry().declared]
|
|
94
|
+
.filter((entry) => entry[1] !== undefined)
|
|
95
|
+
.sort(([, left], [, right]) => right.length - left.length);
|
|
96
|
+
let redacted = text;
|
|
97
|
+
for (const [name, value] of values) {
|
|
98
|
+
redacted = redacted.split(value).join(`[redacted: ${name}]`);
|
|
99
|
+
}
|
|
100
|
+
return redacted;
|
|
101
|
+
}
|
|
102
|
+
// Deliberately not re-exported from `index.ts`. The registry it clears is shared across every
|
|
103
|
+
// copy of this package in the process, so a customer reaching this would be clearing
|
|
104
|
+
// redaction and missing-secret state registered by code that is not theirs. This package's
|
|
105
|
+
// own suite imports it from this module directly, which is all it was ever needed for.
|
|
106
|
+
export function resetSecretsForTesting() {
|
|
107
|
+
registry().declared.clear();
|
|
108
|
+
}
|
|
109
|
+
//# sourceMappingURL=secrets.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"secrets.js","sourceRoot":"","sources":["../src/secrets.ts"],"names":[],"mappings":"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"}
|
package/dist/stack.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stack.d.ts","sourceRoot":"","sources":["../src/stack.ts"],"names":[],"mappings":"AAsBA,wBAAgB,UAAU,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAS/D;AAKD,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,CAAC,GAAG,IAAI,EAAE,KAAK,EAAE,KAAK,OAAO,EACvC,KAAK,EAAE,MAAM,GACZ,CAAC,MAAM,GAAG,SAAS,CAAC,EAAE,CAoBxB"}
|
package/dist/stack.js
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import { isAbsolute } from "node:path";
|
|
2
|
+
import { fileURLToPath } from "node:url";
|
|
3
|
+
// Reading the call stack is how two features here find out where code came from:
|
|
4
|
+
// `defineVendureExtension` takes the file that declared an extension, so a relative
|
|
5
|
+
// `migrations` glob resolves against it, and the outbound-host check takes every frame, so a
|
|
6
|
+
// call can be attributed to the extension that made it. Both want the same two things, and
|
|
7
|
+
// both get them wrong in slightly different ways when each keeps its own copy.
|
|
8
|
+
//
|
|
9
|
+
// Installing our own `prepareStackTrace` does more than give us the frames.
|
|
10
|
+
// `source-map-support` and Node's `--enable-source-maps` both work by replacing that hook, and
|
|
11
|
+
// both would hand back the original `.ts` path. The runtime image runs
|
|
12
|
+
// `node --enable-source-maps` (`apps/vc-builder/src/runtime.ts`), so without this a glob would
|
|
13
|
+
// resolve against a source tree the image does not ship, and an attribution would be measured
|
|
14
|
+
// against a directory that is not the one the code was loaded from.
|
|
15
|
+
// ESM frames carry a file URL and CommonJS frames carry a path, and Bun reports a path for
|
|
16
|
+
// both. Anything else — `node:internal/...`, a `data:` URL, `<anonymous>` from an eval — is
|
|
17
|
+
// not a file on disk and resolves nothing.
|
|
18
|
+
//
|
|
19
|
+
// `isAbsolute` rather than "contains a separator": a specifier like
|
|
20
|
+
// `node:internal/deps/undici/undici` contains one and is still not a file.
|
|
21
|
+
export function toFilePath(fileName) {
|
|
22
|
+
if (fileName.startsWith("file://")) {
|
|
23
|
+
try {
|
|
24
|
+
return fileURLToPath(fileName);
|
|
25
|
+
}
|
|
26
|
+
catch {
|
|
27
|
+
return undefined;
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
return isAbsolute(fileName) ? fileName : undefined;
|
|
31
|
+
}
|
|
32
|
+
// The file each frame above `boundary` came from, nearest first. A frame that names no file
|
|
33
|
+
// on disk is kept as `undefined` rather than dropped, so a caller that wants specifically the
|
|
34
|
+
// first frame — as `defineVendureExtension` does — cannot silently be handed the second.
|
|
35
|
+
export function stackFrameFiles(boundary, limit) {
|
|
36
|
+
const previousPrepare = Error.prepareStackTrace;
|
|
37
|
+
const previousLimit = Error.stackTraceLimit;
|
|
38
|
+
try {
|
|
39
|
+
// Some test runners and instrumentation set `Error.stackTraceLimit` to zero, which yields
|
|
40
|
+
// no frames at all.
|
|
41
|
+
Error.stackTraceLimit = Math.max(previousLimit, limit);
|
|
42
|
+
Error.prepareStackTrace = (_error, frames) => frames;
|
|
43
|
+
const holder = {};
|
|
44
|
+
Error.captureStackTrace(holder, boundary);
|
|
45
|
+
const frames = holder.stack;
|
|
46
|
+
if (!Array.isArray(frames))
|
|
47
|
+
return [];
|
|
48
|
+
return frames.map((frame) => {
|
|
49
|
+
const fileName = frame?.getFileName?.();
|
|
50
|
+
return typeof fileName === "string" ? toFilePath(fileName) : undefined;
|
|
51
|
+
});
|
|
52
|
+
}
|
|
53
|
+
finally {
|
|
54
|
+
Error.prepareStackTrace = previousPrepare;
|
|
55
|
+
Error.stackTraceLimit = previousLimit;
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
//# sourceMappingURL=stack.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stack.js","sourceRoot":"","sources":["../src/stack.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AACvC,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAEzC,iFAAiF;AACjF,oFAAoF;AACpF,6FAA6F;AAC7F,2FAA2F;AAC3F,+EAA+E;AAC/E,EAAE;AACF,4EAA4E;AAC5E,+FAA+F;AAC/F,uEAAuE;AACvE,+FAA+F;AAC/F,8FAA8F;AAC9F,oEAAoE;AAEpE,2FAA2F;AAC3F,4FAA4F;AAC5F,2CAA2C;AAC3C,EAAE;AACF,oEAAoE;AACpE,2EAA2E;AAC3E,MAAM,UAAU,UAAU,CAAC,QAAgB;IACzC,IAAI,QAAQ,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;QACnC,IAAI,CAAC;YACH,OAAO,aAAa,CAAC,QAAQ,CAAC,CAAC;QACjC,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,SAAS,CAAC;QACnB,CAAC;IACH,CAAC;IACD,OAAO,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,CAAC;AACrD,CAAC;AAED,4FAA4F;AAC5F,8FAA8F;AAC9F,yFAAyF;AACzF,MAAM,UAAU,eAAe,CAC7B,QAAuC,EACvC,KAAa;IAEb,MAAM,eAAe,GAAG,KAAK,CAAC,iBAAiB,CAAC;IAChD,MAAM,aAAa,GAAG,KAAK,CAAC,eAAe,CAAC;IAC5C,IAAI,CAAC;QACH,0FAA0F;QAC1F,oBAAoB;QACpB,KAAK,CAAC,eAAe,GAAG,IAAI,CAAC,GAAG,CAAC,aAAa,EAAE,KAAK,CAAC,CAAC;QACvD,KAAK,CAAC,iBAAiB,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC;QACrD,MAAM,MAAM,GAAwB,EAAE,CAAC;QACvC,KAAK,CAAC,iBAAiB,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;QAC1C,MAAM,MAAM,GAAG,MAAM,CAAC,KAAK,CAAC;QAC5B,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC;YAAE,OAAO,EAAE,CAAC;QACtC,OAAO,MAAM,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE;YAC1B,MAAM,QAAQ,GAAY,KAAK,EAAE,WAAW,EAAE,EAAE,CAAC;YACjD,OAAO,OAAO,QAAQ,KAAK,QAAQ,CAAC,CAAC,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACzE,CAAC,CAAC,CAAC;IACL,CAAC;YAAS,CAAC;QACT,KAAK,CAAC,iBAAiB,GAAG,eAAe,CAAC;QAC1C,KAAK,CAAC,eAAe,GAAG,aAAa,CAAC;IACxC,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { CloudConfigError } from "./errors.js";
|
|
2
|
+
import { type ExtensionOfPlugin, type PluginLike } from "./plugin-attribution.js";
|
|
3
|
+
export interface SupersededPlugin {
|
|
4
|
+
plugin: string;
|
|
5
|
+
replacement: string;
|
|
6
|
+
reason: string;
|
|
7
|
+
}
|
|
8
|
+
export declare const SUPERSEDED_PLUGINS: readonly SupersededPlugin[];
|
|
9
|
+
export declare function findSupersededPlugin(name: string): SupersededPlugin | undefined;
|
|
10
|
+
export interface SupersededPluginDeclaration {
|
|
11
|
+
superseded: SupersededPlugin;
|
|
12
|
+
extension?: string;
|
|
13
|
+
}
|
|
14
|
+
export declare class SupersededPluginDeclaredError extends CloudConfigError {
|
|
15
|
+
readonly declarations: readonly SupersededPluginDeclaration[];
|
|
16
|
+
constructor(declarations: readonly SupersededPluginDeclaration[]);
|
|
17
|
+
}
|
|
18
|
+
export declare function assertNoSupersededPluginDeclared(plugins: readonly PluginLike[], extensionOf?: ExtensionOfPlugin): void;
|
|
19
|
+
//# sourceMappingURL=superseded-plugins.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"superseded-plugins.d.ts","sourceRoot":"","sources":["../src/superseded-plugins.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC/C,OAAO,EAAE,KAAK,iBAAiB,EAAE,KAAK,UAAU,EAAc,MAAM,yBAAyB,CAAC;AAkB9F,MAAM,WAAW,gBAAgB;IAI/B,MAAM,EAAE,MAAM,CAAC;IAGf,WAAW,EAAE,MAAM,CAAC;IACpB,MAAM,EAAE,MAAM,CAAC;CAChB;AAWD,eAAO,MAAM,kBAAkB,EAAE,SAAS,gBAAgB,EAAqB,CAAC;AAEhF,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,gBAAgB,GAAG,SAAS,CAE/E;AAED,MAAM,WAAW,2BAA2B;IAC1C,UAAU,EAAE,gBAAgB,CAAC;IAI7B,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,qBAAa,6BAA8B,SAAQ,gBAAgB;IACjE,QAAQ,CAAC,YAAY,EAAE,SAAS,2BAA2B,EAAE,CAAC;gBAElD,YAAY,EAAE,SAAS,2BAA2B,EAAE;CAiBjE;AAED,wBAAgB,gCAAgC,CAC9C,OAAO,EAAE,SAAS,UAAU,EAAE,EAC9B,WAAW,GAAE,iBAA6B,GACzC,IAAI,CAUN"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { CloudConfigError } from "./errors.js";
|
|
2
|
+
import { pluginName } from "./plugin-attribution.js";
|
|
3
|
+
const SUPERSEDED_SPECS = [
|
|
4
|
+
{
|
|
5
|
+
plugin: "DashboardPlugin",
|
|
6
|
+
replacement: "CloudDashboardPlugin",
|
|
7
|
+
reason: "Vendure Cloud serves the Dashboard itself, from a directory that only exists inside the runtime image. CloudDashboardPlugin keeps the route and supplies the rest.",
|
|
8
|
+
},
|
|
9
|
+
];
|
|
10
|
+
export const SUPERSEDED_PLUGINS = SUPERSEDED_SPECS;
|
|
11
|
+
export function findSupersededPlugin(name) {
|
|
12
|
+
return SUPERSEDED_PLUGINS.find((superseded) => superseded.plugin === name);
|
|
13
|
+
}
|
|
14
|
+
export class SupersededPluginDeclaredError extends CloudConfigError {
|
|
15
|
+
declarations;
|
|
16
|
+
constructor(declarations) {
|
|
17
|
+
const detail = declarations
|
|
18
|
+
.map(({ superseded, extension }) => {
|
|
19
|
+
const where = extension === undefined
|
|
20
|
+
? superseded.plugin
|
|
21
|
+
: `${superseded.plugin}, in the Vendure Extension "${extension}",`;
|
|
22
|
+
return ` ${where} is supplied by Vendure Cloud.\n ${superseded.reason}\n Use ${superseded.replacement} instead.`;
|
|
23
|
+
})
|
|
24
|
+
.join("\n\n");
|
|
25
|
+
super(`Vendure Cloud: this configuration declares ${declarations.length} plugin${declarations.length === 1 ? "" : "s"} that the platform supplies. Refusing to boot.\n\n${detail}\n`);
|
|
26
|
+
this.declarations = declarations;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
export function assertNoSupersededPluginDeclared(plugins, extensionOf = new Map()) {
|
|
30
|
+
const declarations = [];
|
|
31
|
+
for (const plugin of plugins) {
|
|
32
|
+
const superseded = findSupersededPlugin(pluginName(plugin));
|
|
33
|
+
if (!superseded)
|
|
34
|
+
continue;
|
|
35
|
+
declarations.push({ superseded, extension: extensionOf.get(plugin)?.id });
|
|
36
|
+
}
|
|
37
|
+
if (declarations.length > 0) {
|
|
38
|
+
throw new SupersededPluginDeclaredError(declarations);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
//# sourceMappingURL=superseded-plugins.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"superseded-plugins.js","sourceRoot":"","sources":["../src/superseded-plugins.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAC/C,OAAO,EAA2C,UAAU,EAAE,MAAM,yBAAyB,CAAC;AA6B9F,MAAM,gBAAgB,GAAG;IACvB;QACE,MAAM,EAAE,iBAAiB;QACzB,WAAW,EAAE,sBAAsB;QACnC,MAAM,EACJ,oKAAoK;KACvK;CAC6C,CAAC;AAEjD,MAAM,CAAC,MAAM,kBAAkB,GAAgC,gBAAgB,CAAC;AAEhF,MAAM,UAAU,oBAAoB,CAAC,IAAY;IAC/C,OAAO,kBAAkB,CAAC,IAAI,CAAC,CAAC,UAAU,EAAE,EAAE,CAAC,UAAU,CAAC,MAAM,KAAK,IAAI,CAAC,CAAC;AAC7E,CAAC;AAUD,MAAM,OAAO,6BAA8B,SAAQ,gBAAgB;IACxD,YAAY,CAAyC;IAE9D,YAAY,YAAoD;QAC9D,MAAM,MAAM,GAAG,YAAY;aACxB,GAAG,CAAC,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,EAAE,EAAE;YACjC,MAAM,KAAK,GACT,SAAS,KAAK,SAAS;gBACrB,CAAC,CAAC,UAAU,CAAC,MAAM;gBACnB,CAAC,CAAC,GAAG,UAAU,CAAC,MAAM,+BAA+B,SAAS,IAAI,CAAC;YACvE,OAAO,KAAK,KAAK,uCAAuC,UAAU,CAAC,MAAM,aAAa,UAAU,CAAC,WAAW,WAAW,CAAC;QAC1H,CAAC,CAAC;aACD,IAAI,CAAC,MAAM,CAAC,CAAC;QAChB,KAAK,CACH,8CAA8C,YAAY,CAAC,MAAM,UAC/D,YAAY,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GACnC,qDAAqD,MAAM,IAAI,CAChE,CAAC;QACF,IAAI,CAAC,YAAY,GAAG,YAAY,CAAC;IACnC,CAAC;CACF;AAED,MAAM,UAAU,gCAAgC,CAC9C,OAA8B,EAC9B,cAAiC,IAAI,GAAG,EAAE;IAE1C,MAAM,YAAY,GAAkC,EAAE,CAAC;IACvD,KAAK,MAAM,MAAM,IAAI,OAAO,EAAE,CAAC;QAC7B,MAAM,UAAU,GAAG,oBAAoB,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC;QAC5D,IAAI,CAAC,UAAU;YAAE,SAAS;QAC1B,YAAY,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,WAAW,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC;IAC5E,CAAC;IACD,IAAI,YAAY,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAC5B,MAAM,IAAI,6BAA6B,CAAC,YAAY,CAAC,CAAC;IACxD,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import type { VendureConfig } from "@vendure/core";
|
|
2
|
+
import { CloudConfigError } from "./errors.js";
|
|
3
|
+
import type { PluginLike } from "./plugin-attribution.js";
|
|
4
|
+
export type VendurePluginEntry = NonNullable<VendureConfig["plugins"]>[number];
|
|
5
|
+
declare const EXTENSION: unique symbol;
|
|
6
|
+
export interface VendureExtensionInput {
|
|
7
|
+
id: string;
|
|
8
|
+
plugins: readonly VendurePluginEntry[];
|
|
9
|
+
migrations?: readonly string[];
|
|
10
|
+
outboundHosts?: readonly string[];
|
|
11
|
+
}
|
|
12
|
+
export interface VendureExtension {
|
|
13
|
+
readonly [EXTENSION]: true;
|
|
14
|
+
readonly id: string;
|
|
15
|
+
readonly plugins: readonly VendurePluginEntry[];
|
|
16
|
+
readonly migrations: readonly string[];
|
|
17
|
+
readonly outboundHosts: readonly string[];
|
|
18
|
+
readonly declaredIn: string | undefined;
|
|
19
|
+
}
|
|
20
|
+
export type CloudPluginEntry = VendurePluginEntry | VendureExtension;
|
|
21
|
+
export declare class InvalidVendureExtensionError extends CloudConfigError {
|
|
22
|
+
}
|
|
23
|
+
export declare class DuplicateVendureExtensionIdError extends CloudConfigError {
|
|
24
|
+
readonly id: string;
|
|
25
|
+
constructor(id: string);
|
|
26
|
+
}
|
|
27
|
+
export declare function defineVendureExtension(extension: VendureExtensionInput): VendureExtension;
|
|
28
|
+
export declare function isVendureExtension(value: unknown): value is VendureExtension;
|
|
29
|
+
export declare function resolveMigrationGlob(extension: VendureExtension, glob: string): string;
|
|
30
|
+
export declare function resolveExtensionMigrations(extension: VendureExtension): string[];
|
|
31
|
+
export interface FlattenedPlugins {
|
|
32
|
+
readonly plugins: readonly VendurePluginEntry[];
|
|
33
|
+
readonly extensions: readonly VendureExtension[];
|
|
34
|
+
readonly extensionOf: ReadonlyMap<PluginLike, VendureExtension>;
|
|
35
|
+
}
|
|
36
|
+
export declare function flattenVendureExtensions(entries: readonly CloudPluginEntry[]): FlattenedPlugins;
|
|
37
|
+
export {};
|
|
38
|
+
//# sourceMappingURL=vendure-extension.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vendure-extension.d.ts","sourceRoot":"","sources":["../src/vendure-extension.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AACnD,OAAO,EAAE,gBAAgB,EAAE,MAAM,aAAa,CAAC;AAE/C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAI1D,MAAM,MAAM,kBAAkB,GAAG,WAAW,CAAC,aAAa,CAAC,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC;AAK/E,QAAA,MAAM,SAAS,eAAgD,CAAC;AAMhE,MAAM,WAAW,qBAAqB;IAIpC,EAAE,EAAE,MAAM,CAAC;IACX,OAAO,EAAE,SAAS,kBAAkB,EAAE,CAAC;IAIvC,UAAU,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAE/B,aAAa,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;CACnC;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,CAAC,SAAS,CAAC,EAAE,IAAI,CAAC;IAC3B,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,OAAO,EAAE,SAAS,kBAAkB,EAAE,CAAC;IAGhD,QAAQ,CAAC,UAAU,EAAE,SAAS,MAAM,EAAE,CAAC;IACvC,QAAQ,CAAC,aAAa,EAAE,SAAS,MAAM,EAAE,CAAC;IAI1C,QAAQ,CAAC,UAAU,EAAE,MAAM,GAAG,SAAS,CAAC;CACzC;AAMD,MAAM,MAAM,gBAAgB,GAAG,kBAAkB,GAAG,gBAAgB,CAAC;AAErE,qBAAa,4BAA6B,SAAQ,gBAAgB;CAAG;AAErE,qBAAa,gCAAiC,SAAQ,gBAAgB;IACpE,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;gBAER,EAAE,EAAE,MAAM;CAMvB;AAuBD,wBAAgB,sBAAsB,CAAC,SAAS,EAAE,qBAAqB,GAAG,gBAAgB,CA4BzF;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,gBAAgB,CAE5E;AASD,wBAAgB,oBAAoB,CAAC,SAAS,EAAE,gBAAgB,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,CAQtF;AAED,wBAAgB,0BAA0B,CAAC,SAAS,EAAE,gBAAgB,GAAG,MAAM,EAAE,CAEhF;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,OAAO,EAAE,SAAS,kBAAkB,EAAE,CAAC;IAChD,QAAQ,CAAC,UAAU,EAAE,SAAS,gBAAgB,EAAE,CAAC;IACjD,QAAQ,CAAC,WAAW,EAAE,WAAW,CAAC,UAAU,EAAE,gBAAgB,CAAC,CAAC;CACjE;AASD,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,SAAS,gBAAgB,EAAE,GAAG,gBAAgB,CAyB/F"}
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
import { dirname, isAbsolute, resolve } from "node:path";
|
|
2
|
+
import { CloudConfigError } from "./errors.js";
|
|
3
|
+
import { stackFrameFiles } from "./stack.js";
|
|
4
|
+
// Registered for the same reason the config handle's symbol is (ADR-0043): a second copy of
|
|
5
|
+
// this package in the tree would otherwise produce extensions that `defineCloudConfig`
|
|
6
|
+
// silently treats as plugins, and core would be handed an object it cannot configure.
|
|
7
|
+
const EXTENSION = Symbol.for("vendure-cloud.vendure-extension");
|
|
8
|
+
export class InvalidVendureExtensionError extends CloudConfigError {
|
|
9
|
+
}
|
|
10
|
+
export class DuplicateVendureExtensionIdError extends CloudConfigError {
|
|
11
|
+
id;
|
|
12
|
+
constructor(id) {
|
|
13
|
+
super(`Vendure Cloud: the Vendure Extension id "${id}" is declared more than once in this configuration.\n An id identifies one extension, so that a boot message can name the extension a plugin came from.\n Give each extension its own id, and declare each extension once.\n`);
|
|
14
|
+
this.id = id;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
// ADR-0047's one mechanical trap: `migrations: ['./migrations/*.js']` written in a package's
|
|
18
|
+
// own index means that package's directory, not the directory of the configuration file that
|
|
19
|
+
// referenced it. `defineVendureExtension` reads the declaring file off the call stack. It
|
|
20
|
+
// does not take `import.meta.url` as an argument, so an author has nothing to pass. An author
|
|
21
|
+
// who copies a declaration into another file and leaves the old value behind gets a glob that
|
|
22
|
+
// matches nothing and raises nothing. Reading the call stack also works whichever module
|
|
23
|
+
// system the build emits, including CommonJS output, where `import.meta` is unavailable.
|
|
24
|
+
//
|
|
25
|
+
// Installing our own `prepareStackTrace` does more than give us the frames.
|
|
26
|
+
// `source-map-support` and Node's `--enable-source-maps` both work by replacing that
|
|
27
|
+
// hook, and both would hand back the original `.ts` path. The runtime image runs
|
|
28
|
+
// `node --enable-source-maps` (`apps/vc-builder/src/runtime.ts`), so without this the glob
|
|
29
|
+
// would resolve against a source tree that the image does not ship. Replacing the hook
|
|
30
|
+
// bypasses them and yields the emitted file, which is what the migrations sit beside.
|
|
31
|
+
function declaringFile(boundary) {
|
|
32
|
+
// The first frame specifically, not the first that happens to name a file: a caller that is
|
|
33
|
+
// not a file on disk has no declaring file, and taking the next frame down would silently
|
|
34
|
+
// hand back whichever of our own callers happened to be beneath it.
|
|
35
|
+
return stackFrameFiles(boundary, 2)[0];
|
|
36
|
+
}
|
|
37
|
+
export function defineVendureExtension(extension) {
|
|
38
|
+
const { id } = extension;
|
|
39
|
+
if (typeof id !== "string" || id.trim() === "" || /\s/.test(id)) {
|
|
40
|
+
throw new InvalidVendureExtensionError(`Vendure Cloud: a Vendure Extension needs an id, and ${JSON.stringify(id)} is not one.\n Give it a short stable name with no spaces, such as 'acme.erp'.\n`);
|
|
41
|
+
}
|
|
42
|
+
const migrations = [...(extension.migrations ?? [])];
|
|
43
|
+
const declaredIn = declaringFile(defineVendureExtension);
|
|
44
|
+
// Raised at definition time rather than when the glob is read. A runtime that cannot report
|
|
45
|
+
// the declaring file then fails on its first run, instead of producing a migration glob that
|
|
46
|
+
// matches nothing.
|
|
47
|
+
if (declaredIn === undefined && migrations.some((glob) => !isAbsolute(glob))) {
|
|
48
|
+
throw new InvalidVendureExtensionError(`Vendure Cloud: the Vendure Extension "${id}" declares migrations as relative globs, and this runtime does not report the file that declared them.\n A relative glob is relative to that file, so it cannot be resolved. Write them as absolute paths instead.\n`);
|
|
49
|
+
}
|
|
50
|
+
return Object.freeze({
|
|
51
|
+
[EXTENSION]: true,
|
|
52
|
+
id,
|
|
53
|
+
plugins: Object.freeze([...extension.plugins]),
|
|
54
|
+
migrations: Object.freeze(migrations),
|
|
55
|
+
outboundHosts: Object.freeze([...(extension.outboundHosts ?? [])]),
|
|
56
|
+
declaredIn,
|
|
57
|
+
});
|
|
58
|
+
}
|
|
59
|
+
export function isVendureExtension(value) {
|
|
60
|
+
return typeof value === "object" && value !== null && EXTENSION in value;
|
|
61
|
+
}
|
|
62
|
+
// String path resolution only; `loadExtensionMigrations` in `migrations.ts` is what reads
|
|
63
|
+
// what the result matches. Recording which extension owns each applied migration on the
|
|
64
|
+
// Deployment row is the other half of ADR-0048 and is CLO-423.
|
|
65
|
+
//
|
|
66
|
+
// Singular as well as plural because the loader reports a glob that matched nothing by the
|
|
67
|
+
// text the author wrote, and pairing that text back up with a positional result would be
|
|
68
|
+
// index arithmetic that can be got wrong.
|
|
69
|
+
export function resolveMigrationGlob(extension, glob) {
|
|
70
|
+
if (isAbsolute(glob))
|
|
71
|
+
return glob;
|
|
72
|
+
if (extension.declaredIn === undefined) {
|
|
73
|
+
throw new InvalidVendureExtensionError(`Vendure Cloud: cannot resolve the migrations glob "${glob}" declared by the Vendure Extension "${extension.id}", because the file that declared it is unknown.\n`);
|
|
74
|
+
}
|
|
75
|
+
return resolve(dirname(extension.declaredIn), glob);
|
|
76
|
+
}
|
|
77
|
+
export function resolveExtensionMigrations(extension) {
|
|
78
|
+
return extension.migrations.map((glob) => resolveMigrationGlob(extension, glob));
|
|
79
|
+
}
|
|
80
|
+
// Turns the array a customer wrote — plugins and extensions mixed — into the flat array core
|
|
81
|
+
// takes, in declaration order, and records which extension each plugin came from so
|
|
82
|
+
// `recordPlatformFieldWrites` can name both.
|
|
83
|
+
//
|
|
84
|
+
// A plugin declared by two extensions maps to the first that declared it. Attribution is
|
|
85
|
+
// per plugin class, because that is where core keeps the configuration function, so there is
|
|
86
|
+
// no finer answer available here. Detecting that overlap at all is CLO-418.
|
|
87
|
+
export function flattenVendureExtensions(entries) {
|
|
88
|
+
const plugins = [];
|
|
89
|
+
const extensions = [];
|
|
90
|
+
const extensionOf = new Map();
|
|
91
|
+
const seenIds = new Set();
|
|
92
|
+
for (const entry of entries) {
|
|
93
|
+
if (!isVendureExtension(entry)) {
|
|
94
|
+
plugins.push(entry);
|
|
95
|
+
continue;
|
|
96
|
+
}
|
|
97
|
+
if (seenIds.has(entry.id)) {
|
|
98
|
+
throw new DuplicateVendureExtensionIdError(entry.id);
|
|
99
|
+
}
|
|
100
|
+
seenIds.add(entry.id);
|
|
101
|
+
extensions.push(entry);
|
|
102
|
+
for (const plugin of entry.plugins) {
|
|
103
|
+
plugins.push(plugin);
|
|
104
|
+
if (!extensionOf.has(plugin)) {
|
|
105
|
+
extensionOf.set(plugin, entry);
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
return { plugins, extensions, extensionOf };
|
|
110
|
+
}
|
|
111
|
+
//# sourceMappingURL=vendure-extension.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vendure-extension.js","sourceRoot":"","sources":["../src/vendure-extension.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@vendure/cloud-config",
|
|
3
|
+
"version": "0.0.0",
|
|
4
|
+
"type": "module",
|
|
5
|
+
"description": "The Cloud Config interface a Vendure Cloud application is written against.",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"homepage": "https://github.com/vendurehq/cloud/tree/main/packages/cloud-config#readme",
|
|
8
|
+
"repository": {
|
|
9
|
+
"type": "git",
|
|
10
|
+
"url": "git+https://github.com/vendurehq/cloud.git",
|
|
11
|
+
"directory": "packages/cloud-config"
|
|
12
|
+
},
|
|
13
|
+
"bugs": {
|
|
14
|
+
"url": "https://github.com/vendurehq/cloud/issues"
|
|
15
|
+
},
|
|
16
|
+
"keywords": [
|
|
17
|
+
"vendure",
|
|
18
|
+
"vendure-cloud",
|
|
19
|
+
"ecommerce",
|
|
20
|
+
"configuration"
|
|
21
|
+
],
|
|
22
|
+
"engines": {
|
|
23
|
+
"node": ">=20.19.0 <21 || >=22.12.0"
|
|
24
|
+
},
|
|
25
|
+
"main": "dist/index.js",
|
|
26
|
+
"types": "dist/index.d.ts",
|
|
27
|
+
"exports": {
|
|
28
|
+
".": {
|
|
29
|
+
"types": "./dist/index.d.ts",
|
|
30
|
+
"import": "./dist/index.js",
|
|
31
|
+
"require": "./dist/index.js"
|
|
32
|
+
}
|
|
33
|
+
},
|
|
34
|
+
"files": [
|
|
35
|
+
"dist",
|
|
36
|
+
"README.md"
|
|
37
|
+
],
|
|
38
|
+
"publishConfig": {
|
|
39
|
+
"access": "public"
|
|
40
|
+
},
|
|
41
|
+
"scripts": {
|
|
42
|
+
"build": "tsc",
|
|
43
|
+
"typecheck": "tsc --noEmit -p tsconfig.test.json",
|
|
44
|
+
"lint": "biome lint ./src ./test",
|
|
45
|
+
"format": "biome format --write ./src ./test",
|
|
46
|
+
"check": "biome check ./src ./test",
|
|
47
|
+
"test": "vitest run",
|
|
48
|
+
"test:all": "vitest run"
|
|
49
|
+
},
|
|
50
|
+
"dependencies": {
|
|
51
|
+
"reflect-metadata": "^0.2.2",
|
|
52
|
+
"tinyglobby": "^0.2.15"
|
|
53
|
+
},
|
|
54
|
+
"peerDependencies": {
|
|
55
|
+
"@vendure/core": "^3.7.0"
|
|
56
|
+
},
|
|
57
|
+
"devDependencies": {
|
|
58
|
+
"@types/node": "^22.20.0",
|
|
59
|
+
"@vendure-cloud/tsconfig": "workspace:*",
|
|
60
|
+
"@vendure/core": "3.7.2",
|
|
61
|
+
"typescript": "catalog:",
|
|
62
|
+
"vitest": "^3.2.6"
|
|
63
|
+
}
|
|
64
|
+
}
|