@supacloud/compiler 0.42.1 → 0.43.1
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 +7 -3
- package/dist/cli.js +967 -398
- package/dist/delivery-bundle-worker.js +11 -0
- package/dist/diagnostics.js +4 -2
- package/dist/fixtures/runtime-source.d.ts +2 -2
- package/dist/index.js +967 -398
- package/dist/migration-app-version.d.ts +1 -1
- package/dist/migration-elysia-version.d.ts +1 -1
- package/dist/source-semantics.d.ts +18 -0
- package/dist/type-safety.d.ts +12 -0
- package/dist/types.d.ts +3 -3
- package/package.json +2 -2
package/dist/cli.js
CHANGED
|
@@ -35,8 +35,8 @@ function getModuleBoundaryProfile(name) {
|
|
|
35
35
|
...profile,
|
|
36
36
|
rules: profile.rules.map((rule) => ({
|
|
37
37
|
...rule,
|
|
38
|
-
|
|
39
|
-
|
|
38
|
+
...rule.onlyDependOnLibsWithTags === undefined ? {} : { onlyDependOnLibsWithTags: [...rule.onlyDependOnLibsWithTags] },
|
|
39
|
+
...rule.bannedDependenciesWithTags === undefined ? {} : { bannedDependenciesWithTags: [...rule.bannedDependenciesWithTags] }
|
|
40
40
|
}))
|
|
41
41
|
};
|
|
42
42
|
}
|
|
@@ -252,7 +252,13 @@ var REQUEST_CONTEXT_TOKEN_NAME = "supacloud.request-context", JOB_CONTEXT_TOKEN_
|
|
|
252
252
|
function validateFeatureSpec(spec, module) {
|
|
253
253
|
const diagnostics = [];
|
|
254
254
|
const error = (code, message) => {
|
|
255
|
-
diagnostics.push({
|
|
255
|
+
diagnostics.push({
|
|
256
|
+
severity: "error",
|
|
257
|
+
code,
|
|
258
|
+
message,
|
|
259
|
+
...spec.file === undefined ? {} : { file: spec.file },
|
|
260
|
+
...spec.line === undefined ? {} : { line: spec.line }
|
|
261
|
+
});
|
|
256
262
|
};
|
|
257
263
|
if (!spec.name.trim() || spec.states.length === 0 || spec.states.some((state) => !state.trim()) || new Set(spec.states).size !== spec.states.length) {
|
|
258
264
|
error("invalid-feature-states", "Feature name and states must be non-empty; states must be unique.");
|
|
@@ -290,7 +296,7 @@ function validateFeatureSpec(spec, module) {
|
|
|
290
296
|
const routes = module.controllers.flatMap((controller) => controller.routes.filter((route) => `${route.method} ${joinRoutePaths(controller.path, route.path)}` === transition.route));
|
|
291
297
|
if (routes.length !== 1) {
|
|
292
298
|
error("feature-route-unresolved", `Transition ${transition.name} must reference exactly one route '${transition.route}' in module ${module.name}.`);
|
|
293
|
-
} else if (command && routes[0]
|
|
299
|
+
} else if (command && routes[0]?.command !== command.className) {
|
|
294
300
|
error("feature-route-drift", `Route ${transition.route} is not bound to ${command.className}.`);
|
|
295
301
|
}
|
|
296
302
|
}
|
|
@@ -2658,7 +2664,7 @@ ${procedureMethods.join(`
|
|
|
2658
2664
|
"",
|
|
2659
2665
|
"function selectResponseSchema(status: number, schemas: Readonly<Record<string, unknown>>): unknown {",
|
|
2660
2666
|
" const family = `${Math.floor(status / 100)}xx`;",
|
|
2661
|
-
|
|
2667
|
+
' return schemas[String(status)] ?? schemas[family] ?? schemas[family.toUpperCase()] ?? schemas["default"];',
|
|
2662
2668
|
"}",
|
|
2663
2669
|
"",
|
|
2664
2670
|
...usesValue ? [
|
|
@@ -2686,16 +2692,16 @@ ${procedureMethods.join(`
|
|
|
2686
2692
|
"function schemaReferenceTarget(ref: string, root: unknown): unknown {",
|
|
2687
2693
|
' const localRef = ref.startsWith("#/$defs/") ? ref.slice(8) : ref.startsWith("#/definitions/") ? ref.slice(14) : ref.startsWith("#/components/schemas/") ? ref.slice(21) : ref.startsWith("#") ? undefined : ref;',
|
|
2688
2694
|
" if (localRef !== undefined && isRecord(root)) {",
|
|
2689
|
-
' const defs = ref.startsWith("#/definitions/") ? root
|
|
2695
|
+
' const defs = ref.startsWith("#/definitions/") ? root["definitions"] : ref.startsWith("#/components/schemas/") ? root["components"] : root["$defs"];',
|
|
2690
2696
|
' if (ref.startsWith("#/components/schemas/") && isRecord(defs)) {',
|
|
2691
|
-
|
|
2697
|
+
' const components = defs["schemas"];',
|
|
2692
2698
|
" if (isRecord(components) && components[localRef] !== undefined) return components[localRef];",
|
|
2693
2699
|
" } else if (isRecord(defs) && defs[localRef] !== undefined) return defs[localRef];",
|
|
2694
2700
|
" }",
|
|
2695
2701
|
" for (const entry of API_SCHEMAS as readonly { name: string; schema: unknown }[]) {",
|
|
2696
2702
|
" if (entry.name === ref) return entry.schema;",
|
|
2697
2703
|
" if (!isRecord(entry.schema)) continue;",
|
|
2698
|
-
|
|
2704
|
+
' if (entry.schema["$id"] === ref || entry.schema["$id"] === localRef) return entry.schema;',
|
|
2699
2705
|
' for (const key of ["$defs", "definitions"] as const) {',
|
|
2700
2706
|
" const defs = entry.schema[key];",
|
|
2701
2707
|
" if (isRecord(defs) && localRef !== undefined && defs[localRef] !== undefined) return defs[localRef];",
|
|
@@ -2722,52 +2728,52 @@ ${procedureMethods.join(`
|
|
|
2722
2728
|
" if (schema === true) return value;",
|
|
2723
2729
|
" if (schema === false || !isRecord(schema)) return schemaError();",
|
|
2724
2730
|
' if ("~codec" in schema || Object.getOwnPropertySymbols(schema).some((symbol) => String(symbol).includes("Transform"))) throw new Error("Response schema transforms are unsupported by the generated decoder");',
|
|
2725
|
-
' if (typeof schema
|
|
2726
|
-
|
|
2727
|
-
|
|
2731
|
+
' if (typeof schema["$ref"] === "string") {',
|
|
2732
|
+
' if (seenRefs.has(schema["$ref"])) return schemaError();',
|
|
2733
|
+
' const target = schemaReferenceTarget(schema["$ref"], root);',
|
|
2728
2734
|
" if (target === undefined) return schemaError();",
|
|
2729
|
-
|
|
2735
|
+
' const nextRefs = new Set(seenRefs); nextRefs.add(schema["$ref"]);',
|
|
2730
2736
|
" return decodeSchemaValue(target, value, root, nextRefs, normalize);",
|
|
2731
2737
|
" }",
|
|
2732
|
-
|
|
2733
|
-
' if (Object.hasOwn(schema, "const") && !sameJsonValue(schema
|
|
2734
|
-
|
|
2735
|
-
|
|
2738
|
+
' if (schema["nullable"] === true && value === null) return value;',
|
|
2739
|
+
' if (Object.hasOwn(schema, "const") && !sameJsonValue(schema["const"], value)) return schemaError();',
|
|
2740
|
+
' if (Array.isArray(schema["enum"]) && !schema["enum"].some((entry) => sameJsonValue(entry, value))) return schemaError();',
|
|
2741
|
+
' if (Array.isArray(schema["anyOf"])) {',
|
|
2736
2742
|
" const matches: unknown[] = [];",
|
|
2737
|
-
|
|
2743
|
+
' for (const variant of schema["anyOf"]) { try { matches.push(decodeSchemaValue(variant, value, root, new Set(seenRefs), normalize)); } catch {} }',
|
|
2738
2744
|
" if (matches.length === 0) return schemaError();",
|
|
2739
2745
|
" return matches[0];",
|
|
2740
2746
|
" }",
|
|
2741
|
-
|
|
2747
|
+
' if (Array.isArray(schema["oneOf"])) {',
|
|
2742
2748
|
" const matches: unknown[] = [];",
|
|
2743
|
-
|
|
2749
|
+
' for (const variant of schema["oneOf"]) { try { matches.push(decodeSchemaValue(variant, value, root, new Set(seenRefs), normalize)); } catch {} }',
|
|
2744
2750
|
" if (matches.length !== 1) return schemaError();",
|
|
2745
2751
|
" return matches[0];",
|
|
2746
2752
|
" }",
|
|
2747
|
-
|
|
2753
|
+
' if (Array.isArray(schema["allOf"])) {',
|
|
2748
2754
|
" let output: unknown = value;",
|
|
2749
|
-
|
|
2755
|
+
' for (const variant of schema["allOf"]) {',
|
|
2750
2756
|
" const decoded = decodeSchemaValue(variant, value, root, new Set(seenRefs), normalize);",
|
|
2751
2757
|
" output = isRecord(output) && isRecord(decoded) ? { ...output, ...decoded } : decoded;",
|
|
2752
2758
|
" }",
|
|
2753
2759
|
" return output;",
|
|
2754
2760
|
" }",
|
|
2755
|
-
|
|
2756
|
-
|
|
2761
|
+
' if (schema["not"] !== undefined) {',
|
|
2762
|
+
' try { decodeSchemaValue(schema["not"], value, root, new Set(seenRefs), normalize); } catch { return value; }',
|
|
2757
2763
|
" return schemaError();",
|
|
2758
2764
|
" }",
|
|
2759
|
-
|
|
2760
|
-
|
|
2765
|
+
' if (Array.isArray(schema["type"])) {',
|
|
2766
|
+
' for (const type of schema["type"]) { try { return decodeSchemaValue({ ...schema, type }, value, root, new Set(seenRefs), normalize); } catch {} }',
|
|
2761
2767
|
" return schemaError();",
|
|
2762
2768
|
" }",
|
|
2763
|
-
' if (schema
|
|
2769
|
+
' if (schema["type"] === "object" || (schema["type"] === undefined && (isRecord(schema["properties"]) || schema["required"] !== undefined))) {',
|
|
2764
2770
|
" if (!isRecord(value)) return schemaError();",
|
|
2765
|
-
|
|
2766
|
-
|
|
2767
|
-
|
|
2771
|
+
' const properties = isRecord(schema["properties"]) ? schema["properties"] : {};',
|
|
2772
|
+
' const patterns = isRecord(schema["patternProperties"]) ? schema["patternProperties"] : {};',
|
|
2773
|
+
' const required = Array.isArray(schema["required"]) ? schema["required"] : [];',
|
|
2768
2774
|
' for (const name of required) if (typeof name === "string" && !Object.hasOwn(value, name)) return schemaError();',
|
|
2769
|
-
' if (typeof schema
|
|
2770
|
-
' if (typeof schema
|
|
2775
|
+
' if (typeof schema["minProperties"] === "number" && Object.keys(value).length < schema["minProperties"]) return schemaError();',
|
|
2776
|
+
' if (typeof schema["maxProperties"] === "number" && Object.keys(value).length > schema["maxProperties"]) return schemaError();',
|
|
2771
2777
|
" const output: Record<string, unknown> = {};",
|
|
2772
2778
|
" for (const [name, item] of Object.entries(value)) {",
|
|
2773
2779
|
" const propertySchema = properties[name];",
|
|
@@ -2778,52 +2784,52 @@ ${procedureMethods.join(`
|
|
|
2778
2784
|
" if (applies) { output[name] = decodeSchemaValue(patternSchema, item, root, new Set<string>(), normalize); matched = true; }",
|
|
2779
2785
|
" }",
|
|
2780
2786
|
" if (matched) continue;",
|
|
2781
|
-
|
|
2787
|
+
' if (schema["additionalProperties"] === false || schema["unevaluatedProperties"] === false || schema["additionalProperties"] === undefined) {',
|
|
2782
2788
|
" if (normalize) continue;",
|
|
2783
2789
|
" return schemaError();",
|
|
2784
2790
|
" }",
|
|
2785
|
-
|
|
2786
|
-
|
|
2791
|
+
' if (isRecord(schema["additionalProperties"])) output[name] = decodeSchemaValue(schema["additionalProperties"], item, root, new Set<string>(), normalize);',
|
|
2792
|
+
' else if (schema["additionalProperties"] === true) output[name] = item;',
|
|
2787
2793
|
" }",
|
|
2788
2794
|
" return output;",
|
|
2789
2795
|
" }",
|
|
2790
|
-
' if (schema
|
|
2796
|
+
' if (schema["type"] === "array") {',
|
|
2791
2797
|
" if (!Array.isArray(value)) return schemaError();",
|
|
2792
|
-
' if (typeof schema
|
|
2793
|
-
' if (typeof schema
|
|
2794
|
-
|
|
2795
|
-
|
|
2798
|
+
' if (typeof schema["minItems"] === "number" && value.length < schema["minItems"]) return schemaError();',
|
|
2799
|
+
' if (typeof schema["maxItems"] === "number" && value.length > schema["maxItems"]) return schemaError();',
|
|
2800
|
+
' if (schema["uniqueItems"] === true) { const keys = value.map((item) => JSON.stringify(item)); if (new Set(keys).size !== keys.length) return schemaError(); }',
|
|
2801
|
+
' const tuple = Array.isArray(schema["prefixItems"]) ? schema["prefixItems"] : Array.isArray(schema["items"]) ? schema["items"] : undefined;',
|
|
2796
2802
|
" if (tuple) {",
|
|
2797
|
-
|
|
2798
|
-
|
|
2803
|
+
' if (schema["additionalItems"] === false && value.length > tuple.length) return schemaError();',
|
|
2804
|
+
' return value.map((item, index) => index < tuple.length ? decodeSchemaValue(tuple[index], item, root, new Set<string>(), normalize) : schema["items"] && !Array.isArray(schema["items"]) ? decodeSchemaValue(schema["items"], item, root, new Set<string>(), normalize) : item);',
|
|
2799
2805
|
" }",
|
|
2800
|
-
|
|
2801
|
-
|
|
2802
|
-
|
|
2806
|
+
' if (schema["items"] === undefined || schema["items"] === true) return value;',
|
|
2807
|
+
' if (schema["items"] === false && value.length > 0) return schemaError();',
|
|
2808
|
+
' return value.map((item) => decodeSchemaValue(schema["items"], item, root, new Set<string>(), normalize));',
|
|
2803
2809
|
" }",
|
|
2804
|
-
' if (schema
|
|
2810
|
+
' if (schema["type"] === "string") {',
|
|
2805
2811
|
' if (typeof value !== "string") return schemaError();',
|
|
2806
|
-
' if (typeof schema
|
|
2807
|
-
' if (typeof schema
|
|
2808
|
-
' if (typeof schema
|
|
2809
|
-
|
|
2812
|
+
' if (typeof schema["minLength"] === "number" && value.length < schema["minLength"]) return schemaError();',
|
|
2813
|
+
' if (typeof schema["maxLength"] === "number" && value.length > schema["maxLength"]) return schemaError();',
|
|
2814
|
+
' if (typeof schema["pattern"] === "string") { let matches = false; try { matches = new RegExp(schema["pattern"]).test(value); } catch { return schemaError(); } if (!matches) return schemaError(); }',
|
|
2815
|
+
' if (!matchesFormat(schema["format"], value)) return schemaError();',
|
|
2810
2816
|
" return value;",
|
|
2811
2817
|
" }",
|
|
2812
|
-
' if (schema
|
|
2813
|
-
' if (schema
|
|
2814
|
-
' if (typeof value !== "number" || !Number.isFinite(value) || (schema
|
|
2815
|
-
' if (typeof schema
|
|
2816
|
-
' if (typeof schema
|
|
2817
|
-
' if (typeof schema
|
|
2818
|
-
' if (typeof schema
|
|
2819
|
-
' if (schema
|
|
2820
|
-
' if (schema
|
|
2821
|
-
' if (typeof schema
|
|
2818
|
+
' if (schema["type"] === "boolean") { if (typeof value !== "boolean") return schemaError(); return value; }',
|
|
2819
|
+
' if (schema["type"] === "number" || schema["type"] === "integer") {',
|
|
2820
|
+
' if (typeof value !== "number" || !Number.isFinite(value) || (schema["type"] === "integer" && !Number.isInteger(value))) return schemaError();',
|
|
2821
|
+
' if (typeof schema["minimum"] === "number" && value < schema["minimum"]) return schemaError();',
|
|
2822
|
+
' if (typeof schema["maximum"] === "number" && value > schema["maximum"]) return schemaError();',
|
|
2823
|
+
' if (typeof schema["exclusiveMinimum"] === "number" && value <= schema["exclusiveMinimum"]) return schemaError();',
|
|
2824
|
+
' if (typeof schema["exclusiveMaximum"] === "number" && value >= schema["exclusiveMaximum"]) return schemaError();',
|
|
2825
|
+
' if (schema["exclusiveMinimum"] === true && typeof schema["minimum"] === "number" && value <= schema["minimum"]) return schemaError();',
|
|
2826
|
+
' if (schema["exclusiveMaximum"] === true && typeof schema["maximum"] === "number" && value >= schema["maximum"]) return schemaError();',
|
|
2827
|
+
' if (typeof schema["multipleOf"] === "number" && schema["multipleOf"] > 0 && Math.abs(value / schema["multipleOf"] - Math.round(value / schema["multipleOf"])) > 1e-9) return schemaError();',
|
|
2822
2828
|
" return value;",
|
|
2823
2829
|
" }",
|
|
2824
|
-
' if (schema
|
|
2825
|
-
' if (schema
|
|
2826
|
-
' if (schema
|
|
2830
|
+
' if (schema["type"] === "null") { if (value !== null) return schemaError(); return value; }',
|
|
2831
|
+
' if (schema["type"] === "void" || schema["type"] === "undefined") { if (value !== undefined) return schemaError(); return value; }',
|
|
2832
|
+
' if (schema["type"] === "never") return schemaError();',
|
|
2827
2833
|
" return value;",
|
|
2828
2834
|
"}",
|
|
2829
2835
|
""
|
|
@@ -2897,7 +2903,7 @@ ${procedureMethods.join(`
|
|
|
2897
2903
|
" ...options.headers,",
|
|
2898
2904
|
" };",
|
|
2899
2905
|
' if (options.cookie && !Object.keys(headers).some((key) => key.toLowerCase() === "cookie")) {',
|
|
2900
|
-
' headers
|
|
2906
|
+
' headers["cookie"] = Object.entries(options.cookie).map(([key, value]) => `${key}=${encodeURIComponent(String(value))}`).join("; " );',
|
|
2901
2907
|
" }",
|
|
2902
2908
|
" const interceptors = config.interceptors ?? [];",
|
|
2903
2909
|
" const executeChain = (",
|
|
@@ -3088,7 +3094,7 @@ function renderOpenApi(graph, options) {
|
|
|
3088
3094
|
for (const module of graph.modules) {
|
|
3089
3095
|
for (const controller of module.controllers) {
|
|
3090
3096
|
for (const route of controller.routes) {
|
|
3091
|
-
const documentation = route.data?.openapi;
|
|
3097
|
+
const documentation = route.data?.["openapi"];
|
|
3092
3098
|
if (documentation !== null && typeof documentation === "object" && "hide" in documentation && documentation.hide === true)
|
|
3093
3099
|
continue;
|
|
3094
3100
|
const fullPath = joinRoutePaths(controller.path, route.path);
|
|
@@ -3275,11 +3281,11 @@ function renderOpenApi(graph, options) {
|
|
|
3275
3281
|
"function isUndefinedSchema(value: unknown, seen = new WeakSet<object>(), refs = new Set<string>(), scope?: unknown): boolean {",
|
|
3276
3282
|
" if (!isRecord(value) || seen.has(value)) return false;",
|
|
3277
3283
|
" seen.add(value);",
|
|
3278
|
-
|
|
3284
|
+
' const nextScope = isRecord(value["$defs"]) || isRecord(value["definitions"]) ? value : scope;',
|
|
3279
3285
|
" try {",
|
|
3280
|
-
' if (value
|
|
3281
|
-
' if (Array.isArray(value
|
|
3282
|
-
' const ref = typeof value
|
|
3286
|
+
' if (value["type"] === "undefined") return true;',
|
|
3287
|
+
' if (Array.isArray(value["type"]) && value["type"].length > 0 && value["type"].every((type) => type === "undefined")) return true;',
|
|
3288
|
+
' const ref = typeof value["$ref"] === "string" ? value["$ref"] : undefined;',
|
|
3283
3289
|
" if (ref !== undefined && !refs.has(ref)) {",
|
|
3284
3290
|
" const target = openApiSchemaRefTarget(ref, nextScope);",
|
|
3285
3291
|
" if (target !== undefined) {",
|
|
@@ -3303,10 +3309,10 @@ function renderOpenApi(graph, options) {
|
|
|
3303
3309
|
"function cloneSchema(value: unknown, seen = new WeakSet<object>(), scope?: unknown): OpenApiSchema {",
|
|
3304
3310
|
" if (!isRecord(value)) return {};",
|
|
3305
3311
|
" if (seen.has(value)) return {};",
|
|
3306
|
-
|
|
3312
|
+
' const nextScope = isRecord(value["$defs"]) || isRecord(value["definitions"]) ? value : scope;',
|
|
3307
3313
|
" if (isUndefinedSchema(value, new WeakSet<object>(), new Set<string>(), nextScope)) return {};",
|
|
3308
3314
|
" seen.add(value);",
|
|
3309
|
-
' if (value
|
|
3315
|
+
' if (value["type"] === "void" || value["type"] === "undefined") { seen.delete(value); return {}; }',
|
|
3310
3316
|
" const allowed = new Set([",
|
|
3311
3317
|
' "$id", "$ref", "$schema", "$defs", "definitions", "title", "description", "type", "enum", "const", "examples", "default",',
|
|
3312
3318
|
' "deprecated", "readOnly", "writeOnly", "format", "pattern", "minLength", "maxLength", "minimum",',
|
|
@@ -3353,12 +3359,12 @@ function renderOpenApi(graph, options) {
|
|
|
3353
3359
|
"function schemaAllowsUndefined(value: unknown, seen = new WeakSet<object>(), refs = new Set<string>(), scope?: unknown): boolean {",
|
|
3354
3360
|
" if (!isRecord(value) || seen.has(value)) return false;",
|
|
3355
3361
|
" seen.add(value);",
|
|
3356
|
-
|
|
3362
|
+
' const nextScope = isRecord(value["$defs"]) || isRecord(value["definitions"]) ? value : scope;',
|
|
3357
3363
|
" try {",
|
|
3358
3364
|
' if (Object.getOwnPropertySymbols(value).some((symbol) => String(symbol).toLowerCase().includes("optional"))) return true;',
|
|
3359
|
-
' if (value
|
|
3360
|
-
' if (Array.isArray(value
|
|
3361
|
-
' const ref = typeof value
|
|
3365
|
+
' if (value["type"] === "undefined") return true;',
|
|
3366
|
+
' if (Array.isArray(value["type"]) && value["type"].includes("undefined")) return true;',
|
|
3367
|
+
' const ref = typeof value["$ref"] === "string" ? value["$ref"] : undefined;',
|
|
3362
3368
|
" if (ref !== undefined && !refs.has(ref)) {",
|
|
3363
3369
|
" const target = openApiSchemaRefTarget(ref, nextScope);",
|
|
3364
3370
|
" if (target !== undefined) {",
|
|
@@ -3378,11 +3384,11 @@ function renderOpenApi(graph, options) {
|
|
|
3378
3384
|
"",
|
|
3379
3385
|
"function resolveRegistrySchema(value: unknown, seen = new Set<string>()): OpenApiSchema {",
|
|
3380
3386
|
" const schema = cloneSchema(value);",
|
|
3381
|
-
' const ref = typeof schema
|
|
3387
|
+
' const ref = typeof schema["$ref"] === "string" ? schema["$ref"] : undefined;',
|
|
3382
3388
|
" if (!ref || seen.has(ref)) return schema;",
|
|
3383
3389
|
' const localName = ref.startsWith("#/components/schemas/") ? ref.slice(21) : ref.startsWith("#/$defs/") ? ref.slice(8) : ref.startsWith("#/definitions/") ? ref.slice(14) : ref;',
|
|
3384
3390
|
' if (ref.startsWith("#/$defs/") || ref.startsWith("#/definitions/")) {',
|
|
3385
|
-
' const defs = ref.startsWith("#/$defs/") ? schema
|
|
3391
|
+
' const defs = ref.startsWith("#/$defs/") ? schema["$defs"] : schema["definitions"];',
|
|
3386
3392
|
" if (isRecord(defs) && defs[localName] !== undefined) return resolveRegistrySchema(defs[localName], new Set([...seen, ref]));",
|
|
3387
3393
|
" }",
|
|
3388
3394
|
" for (const [name, candidate] of Object.entries(OPENAPI_SCHEMA_REGISTRY)) {",
|
|
@@ -3395,18 +3401,18 @@ function renderOpenApi(graph, options) {
|
|
|
3395
3401
|
"",
|
|
3396
3402
|
"function schemaProperty(schema: unknown, name: string): OpenApiSchema {",
|
|
3397
3403
|
" const document = resolveRegistrySchema(schema);",
|
|
3398
|
-
|
|
3404
|
+
' const properties = document["properties"];',
|
|
3399
3405
|
' return isRecord(properties) && isRecord(properties[name]) ? properties[name] : { type: "string" };',
|
|
3400
3406
|
"}",
|
|
3401
3407
|
"",
|
|
3402
3408
|
"function schemaPropertyNames(schema: unknown): string[] {",
|
|
3403
3409
|
" const document = resolveRegistrySchema(schema);",
|
|
3404
|
-
|
|
3410
|
+
' return isRecord(document["properties"]) ? Object.keys(document["properties"]).sort() : [];',
|
|
3405
3411
|
"}",
|
|
3406
3412
|
"",
|
|
3407
3413
|
"function schemaRequired(schema: unknown, name: string): boolean {",
|
|
3408
3414
|
" const document = resolveRegistrySchema(schema);",
|
|
3409
|
-
|
|
3415
|
+
' return Array.isArray(document["required"]) && document["required"].includes(name);',
|
|
3410
3416
|
"}",
|
|
3411
3417
|
"",
|
|
3412
3418
|
"function schemaReference(name: string): OpenApiSchema {",
|
|
@@ -4051,24 +4057,24 @@ function assertGraphqlOptions(value) {
|
|
|
4051
4057
|
if (unsupported.length) {
|
|
4052
4058
|
fail(`Unsupported options: ${unsupported.join(", ")}. Configure only schema, documents, scalars and typedDocuments; server schema authoring modes are not supported.`);
|
|
4053
4059
|
}
|
|
4054
|
-
const schema = options
|
|
4060
|
+
const schema = options["schema"];
|
|
4055
4061
|
if (typeof schema !== "string" || !schema.trim() || schema !== schema.trim() || /[\r\n\0]/.test(schema) || /^[a-z][a-z0-9+.-]*:/i.test(schema) && !/^[a-z]:[\\/]/i.test(schema) || ![".graphql", ".gql", ".json"].includes(extname(schema))) {
|
|
4056
4062
|
fail("graphql.schema must be a local .graphql, .gql or .json database snapshot. Export it with graphql-schema; URLs, inline SDL and executable schema sources are not supported.");
|
|
4057
4063
|
}
|
|
4058
|
-
if (options
|
|
4064
|
+
if (options["documents"] !== undefined && (!Array.isArray(options["documents"]) || options["documents"].some((pattern) => typeof pattern !== "string" || !pattern.trim()))) {
|
|
4059
4065
|
fail("graphql.documents must contain local query/fragment glob strings.");
|
|
4060
4066
|
}
|
|
4061
|
-
if (options
|
|
4067
|
+
if (options["typedDocuments"] !== undefined && typeof options["typedDocuments"] !== "boolean") {
|
|
4062
4068
|
fail("graphql.typedDocuments must be a boolean output option.");
|
|
4063
4069
|
}
|
|
4064
|
-
if (options
|
|
4070
|
+
if (options["mutations"] !== undefined && typeof options["mutations"] !== "boolean") {
|
|
4065
4071
|
fail("graphql.mutations must be a boolean opt-in for database-backed mutation documents.");
|
|
4066
4072
|
}
|
|
4067
|
-
if (options
|
|
4068
|
-
if (!options
|
|
4073
|
+
if (options["scalars"] !== undefined) {
|
|
4074
|
+
if (!options["scalars"] || typeof options["scalars"] !== "object" || Array.isArray(options["scalars"])) {
|
|
4069
4075
|
fail("graphql.scalars must be a map of explicit wire types.");
|
|
4070
4076
|
}
|
|
4071
|
-
for (const mapping of Object.values(options
|
|
4077
|
+
for (const mapping of Object.values(options["scalars"])) {
|
|
4072
4078
|
if (typeof mapping === "string" && mapping.trim())
|
|
4073
4079
|
continue;
|
|
4074
4080
|
if (mapping && typeof mapping === "object" && !Array.isArray(mapping) && "input" in mapping && typeof mapping.input === "string" && mapping.input.trim() && "output" in mapping && typeof mapping.output === "string" && mapping.output.trim())
|
|
@@ -4091,7 +4097,7 @@ var init_graphql_options = __esm(() => {
|
|
|
4091
4097
|
|
|
4092
4098
|
// src/graphql-inputs.ts
|
|
4093
4099
|
import { resolve as resolve5 } from "node:path";
|
|
4094
|
-
import * as
|
|
4100
|
+
import * as ts11 from "@typescript/typescript6";
|
|
4095
4101
|
function graphqlInputPaths(options) {
|
|
4096
4102
|
if (!options.graphql)
|
|
4097
4103
|
return [];
|
|
@@ -4102,7 +4108,7 @@ function graphqlInputPaths(options) {
|
|
|
4102
4108
|
}
|
|
4103
4109
|
const root = resolve5(options.rootDir);
|
|
4104
4110
|
const schema = resolve5(root, options.graphql.schema);
|
|
4105
|
-
const documents =
|
|
4111
|
+
const documents = ts11.sys.readDirectory(root, [".graphql", ".gql"], ["**/node_modules/**", "**/.git/**", resolve5(options.outDir)], options.graphql.documents ?? ["**/*.graphql", "**/*.gql"]).map((path) => resolve5(path)).filter((path) => path !== schema);
|
|
4106
4112
|
return [schema, ...[...new Set(documents)].sort()];
|
|
4107
4113
|
}
|
|
4108
4114
|
var init_graphql_inputs = __esm(() => {
|
|
@@ -4110,7 +4116,7 @@ var init_graphql_inputs = __esm(() => {
|
|
|
4110
4116
|
});
|
|
4111
4117
|
|
|
4112
4118
|
// src/graphql-runtime.ts
|
|
4113
|
-
import * as
|
|
4119
|
+
import * as ts12 from "@typescript/typescript6";
|
|
4114
4120
|
import { resolve as resolve6 } from "node:path";
|
|
4115
4121
|
function renderGraphqlValidators(source, operationNames, operationKinds = new Map) {
|
|
4116
4122
|
const fileName = resolve6("/__supacloud_graphql__/contracts.ts");
|
|
@@ -4122,18 +4128,18 @@ function renderGraphqlValidators(source, operationNames, operationKinds = new Ma
|
|
|
4122
4128
|
noPropertyAccessFromIndexSignature: true,
|
|
4123
4129
|
noFallthroughCasesInSwitch: true,
|
|
4124
4130
|
skipLibCheck: false,
|
|
4125
|
-
target:
|
|
4131
|
+
target: ts12.ScriptTarget.ES2022,
|
|
4126
4132
|
lib: ["lib.es2022.d.ts"],
|
|
4127
4133
|
types: [],
|
|
4128
4134
|
noEmit: true
|
|
4129
4135
|
};
|
|
4130
|
-
const host =
|
|
4136
|
+
const host = ts12.createCompilerHost(options);
|
|
4131
4137
|
const getSourceFile = host.getSourceFile.bind(host);
|
|
4132
|
-
host.getSourceFile = (path, languageVersion, onError, shouldCreateNewSourceFile) => resolve6(path) === fileName ?
|
|
4133
|
-
const program =
|
|
4134
|
-
const diagnostics =
|
|
4138
|
+
host.getSourceFile = (path, languageVersion, onError, shouldCreateNewSourceFile) => resolve6(path) === fileName ? ts12.createSourceFile(path, source, languageVersion, true) : getSourceFile(path, languageVersion, onError, shouldCreateNewSourceFile);
|
|
4139
|
+
const program = ts12.createProgram([fileName], options, host);
|
|
4140
|
+
const diagnostics = ts12.getPreEmitDiagnostics(program);
|
|
4135
4141
|
if (diagnostics.length) {
|
|
4136
|
-
throw new Error(`Generated GraphQL types cannot be validated: ${diagnostics.map((item) =>
|
|
4142
|
+
throw new Error(`Generated GraphQL types cannot be validated: ${diagnostics.map((item) => ts12.flattenDiagnosticMessageText(item.messageText, `
|
|
4137
4143
|
`)).join("; ")}`);
|
|
4138
4144
|
}
|
|
4139
4145
|
const checker = program.getTypeChecker();
|
|
@@ -4163,25 +4169,25 @@ function renderGraphqlValidators(source, operationNames, operationKinds = new Ma
|
|
|
4163
4169
|
return name;
|
|
4164
4170
|
}
|
|
4165
4171
|
function expression(type) {
|
|
4166
|
-
if (type.flags &
|
|
4172
|
+
if (type.flags & ts12.TypeFlags.Any)
|
|
4167
4173
|
return unsupported(type);
|
|
4168
|
-
if (type.flags &
|
|
4174
|
+
if (type.flags & ts12.TypeFlags.Unknown)
|
|
4169
4175
|
return "true";
|
|
4170
|
-
if (type.flags &
|
|
4176
|
+
if (type.flags & ts12.TypeFlags.Never)
|
|
4171
4177
|
return "false";
|
|
4172
|
-
if (type.flags &
|
|
4178
|
+
if (type.flags & ts12.TypeFlags.Null)
|
|
4173
4179
|
return "value === null";
|
|
4174
|
-
if (type.flags &
|
|
4180
|
+
if (type.flags & ts12.TypeFlags.Undefined)
|
|
4175
4181
|
return "value === undefined";
|
|
4176
4182
|
if (type.isStringLiteral() || type.isNumberLiteral())
|
|
4177
4183
|
return `value === ${JSON.stringify(type.value)}`;
|
|
4178
|
-
if (type.flags &
|
|
4184
|
+
if (type.flags & ts12.TypeFlags.BooleanLiteral)
|
|
4179
4185
|
return `value === ${checker.typeToString(type)}`;
|
|
4180
|
-
if (type.flags &
|
|
4186
|
+
if (type.flags & ts12.TypeFlags.String)
|
|
4181
4187
|
return 'typeof value === "string"';
|
|
4182
|
-
if (type.flags &
|
|
4188
|
+
if (type.flags & ts12.TypeFlags.Number)
|
|
4183
4189
|
return 'typeof value === "number" && Number.isFinite(value)';
|
|
4184
|
-
if (type.flags &
|
|
4190
|
+
if (type.flags & ts12.TypeFlags.Boolean)
|
|
4185
4191
|
return 'typeof value === "boolean"';
|
|
4186
4192
|
if (type.isUnion())
|
|
4187
4193
|
return type.types.map((part) => `${reference(part)}(value)`).join(" || ");
|
|
@@ -4190,16 +4196,16 @@ function renderGraphqlValidators(source, operationNames, operationKinds = new Ma
|
|
|
4190
4196
|
if (checker.isTupleType(type))
|
|
4191
4197
|
return unsupported(type);
|
|
4192
4198
|
if (checker.isArrayType(type)) {
|
|
4193
|
-
const item = checker.getIndexTypeOfType(type,
|
|
4199
|
+
const item = checker.getIndexTypeOfType(type, ts12.IndexKind.Number);
|
|
4194
4200
|
if (!item)
|
|
4195
4201
|
return unsupported(type);
|
|
4196
4202
|
return `isGraphqlArray(value) && Array.from(value).every(${reference(item)})`;
|
|
4197
4203
|
}
|
|
4198
|
-
if (type.flags &
|
|
4204
|
+
if (type.flags & ts12.TypeFlags.Object) {
|
|
4199
4205
|
if (type.getCallSignatures().length || type.getConstructSignatures().length)
|
|
4200
4206
|
return unsupported(type);
|
|
4201
4207
|
const indexes = checker.getIndexInfosOfType(type);
|
|
4202
|
-
if (indexes.some((index) => !(index.keyType.flags &
|
|
4208
|
+
if (indexes.some((index) => !(index.keyType.flags & ts12.TypeFlags.String)))
|
|
4203
4209
|
return unsupported(type);
|
|
4204
4210
|
const properties = checker.getPropertiesOfType(type).map((property) => {
|
|
4205
4211
|
const declaration = property.valueDeclaration ?? property.declarations?.[0];
|
|
@@ -4208,7 +4214,7 @@ function renderGraphqlValidators(source, operationNames, operationKinds = new Ma
|
|
|
4208
4214
|
const check = reference(checker.getTypeOfSymbolAtLocation(property, declaration));
|
|
4209
4215
|
const key = JSON.stringify(property.name);
|
|
4210
4216
|
const present = `Object.prototype.hasOwnProperty.call(value, ${key})`;
|
|
4211
|
-
return property.flags &
|
|
4217
|
+
return property.flags & ts12.SymbolFlags.Optional ? `(!${present} || ${check}(value[${key}]))` : `(${present} && ${check}(value[${key}]))`;
|
|
4212
4218
|
});
|
|
4213
4219
|
const indexedValues = indexes.map((index) => `Object.values(value).every(${reference(index.type)})`);
|
|
4214
4220
|
return ["isGraphqlRecord(value)", ...properties, ...indexedValues].join(" && ");
|
|
@@ -4346,8 +4352,8 @@ async function renderGraphql(options) {
|
|
|
4346
4352
|
severity: "error",
|
|
4347
4353
|
code,
|
|
4348
4354
|
message: error instanceof Error ? error.message : String(error),
|
|
4349
|
-
|
|
4350
|
-
|
|
4355
|
+
...source === undefined ? {} : { file: localPath(source) },
|
|
4356
|
+
...gql?.locations?.[0]?.line === undefined ? {} : { line: gql.locations[0].line },
|
|
4351
4357
|
suggestion: "Update the role-scoped local schema snapshot or correct the query, then recompile."
|
|
4352
4358
|
});
|
|
4353
4359
|
};
|
|
@@ -4397,8 +4403,8 @@ async function renderGraphql(options) {
|
|
|
4397
4403
|
severity: "error",
|
|
4398
4404
|
code: "graphql-query-only",
|
|
4399
4405
|
message: "GraphQL subscriptions are not supported by the HTTP contract compiler. Use the governed Realtime transport for subscriptions.",
|
|
4400
|
-
|
|
4401
|
-
line: definition.loc
|
|
4406
|
+
...definition.loc ? { file: localPath(definition.loc.source.name) } : {},
|
|
4407
|
+
...definition.loc?.startToken.line === undefined ? {} : { line: definition.loc.startToken.line },
|
|
4402
4408
|
suggestion: "Remove this subscription from the GraphQL documents and use the supported Realtime contract."
|
|
4403
4409
|
});
|
|
4404
4410
|
} else if (definition.operation === "mutation" && !options.graphql.mutations) {
|
|
@@ -4406,8 +4412,8 @@ async function renderGraphql(options) {
|
|
|
4406
4412
|
severity: "error",
|
|
4407
4413
|
code: "graphql-query-only",
|
|
4408
4414
|
message: "GraphQL mutations are disabled by default. Set graphql.mutations to true only after reviewing database grants, RLS, audit and idempotency behavior.",
|
|
4409
|
-
|
|
4410
|
-
line: definition.loc
|
|
4415
|
+
...definition.loc ? { file: localPath(definition.loc.source.name) } : {},
|
|
4416
|
+
...definition.loc?.startToken.line === undefined ? {} : { line: definition.loc.startToken.line },
|
|
4411
4417
|
suggestion: "Keep business writes in the governed Command API, or explicitly opt in with graphql.mutations: true."
|
|
4412
4418
|
});
|
|
4413
4419
|
}
|
|
@@ -5517,11 +5523,22 @@ var init_dependent = __esm(() => {
|
|
|
5517
5523
|
});
|
|
5518
5524
|
|
|
5519
5525
|
// node_modules/typebox/build/type/engine/enum/typescript_enum_to_enum_values.mjs
|
|
5526
|
+
function IsTypeScriptEnumLike(value) {
|
|
5527
|
+
return IsObjectNotArray(value);
|
|
5528
|
+
}
|
|
5529
|
+
function TypeScriptEnumToEnumValues(type) {
|
|
5530
|
+
const keys = Keys(type).filter((key) => isNaN(key));
|
|
5531
|
+
return keys.reduce((result, key) => [...result, type[key]], []);
|
|
5532
|
+
}
|
|
5520
5533
|
var init_typescript_enum_to_enum_values = __esm(() => {
|
|
5521
5534
|
init_guard2();
|
|
5522
5535
|
});
|
|
5523
5536
|
|
|
5524
5537
|
// node_modules/typebox/build/type/types/enum.mjs
|
|
5538
|
+
function Enum(value, options) {
|
|
5539
|
+
const values = IsTypeScriptEnumLike(value) ? TypeScriptEnumToEnumValues(value) : value;
|
|
5540
|
+
return Create({ "~kind": "Enum" }, { enum: values }, options);
|
|
5541
|
+
}
|
|
5525
5542
|
function IsEnum(value) {
|
|
5526
5543
|
return IsKind(value, "Enum");
|
|
5527
5544
|
}
|
|
@@ -14826,6 +14843,12 @@ function createExecutionSnapshot(graph, subjects = graph.modules.map((module) =>
|
|
|
14826
14843
|
contexts: subjects.map((subject) => {
|
|
14827
14844
|
const context = createContextPack(graph, subject);
|
|
14828
14845
|
const owner = graph.modules.find((module) => module.name === context.subject);
|
|
14846
|
+
if (owner === undefined)
|
|
14847
|
+
throw new Error(`Execution context owner is missing: ${context.subject}`);
|
|
14848
|
+
const modules = context.modules.map((module) => {
|
|
14849
|
+
const file = executionSourceFile(module.file);
|
|
14850
|
+
return { name: module.name, ...file === undefined ? {} : { file } };
|
|
14851
|
+
});
|
|
14829
14852
|
return {
|
|
14830
14853
|
subject: context.subject,
|
|
14831
14854
|
aliases: [...new Set([
|
|
@@ -14836,10 +14859,7 @@ function createExecutionSnapshot(graph, subjects = graph.modules.map((module) =>
|
|
|
14836
14859
|
...(owner.jobs ?? []).flatMap((job) => [job.name, job.className, job.serviceKey]),
|
|
14837
14860
|
...owner.queries.flatMap((query) => [query.name, query.className])
|
|
14838
14861
|
])],
|
|
14839
|
-
modules
|
|
14840
|
-
name: module.name,
|
|
14841
|
-
...executionSourceFile(module.file) ? { file: executionSourceFile(module.file) } : {}
|
|
14842
|
-
})),
|
|
14862
|
+
modules,
|
|
14843
14863
|
files: context.files,
|
|
14844
14864
|
diagnostics: context.diagnostics.map((diagnostic) => {
|
|
14845
14865
|
const repair = createDiagnosticRepairPlan([diagnostic])[0];
|
|
@@ -15004,21 +15024,21 @@ function requestIdentifier(input) {
|
|
|
15004
15024
|
}
|
|
15005
15025
|
function decodeMetadata(input) {
|
|
15006
15026
|
const envelope = record4(input);
|
|
15007
|
-
if (Object.keys(envelope).some((key) => key !== "version" && key !== "events") || envelope
|
|
15027
|
+
if (Object.keys(envelope).some((key) => key !== "version" && key !== "events") || envelope["version"] !== 1 || !Array.isArray(envelope["events"]) || envelope["events"].length > EXECUTION_CONTEXT_LIMITS.inputEvents)
|
|
15008
15028
|
return invalid();
|
|
15009
|
-
const events = envelope
|
|
15029
|
+
const events = envelope["events"].map((entry) => {
|
|
15010
15030
|
const event = record4(entry);
|
|
15011
|
-
if (Object.keys(event).some((key) => !["kind", "operation", "stage", "phase", "requestId", "durationMs", "attempt", "traceId"].includes(key)) || event
|
|
15031
|
+
if (Object.keys(event).some((key) => !["kind", "operation", "stage", "phase", "requestId", "durationMs", "attempt", "traceId"].includes(key)) || event["kind"] !== "route" && event["kind"] !== "command" && event["kind"] !== "job" || event["phase"] !== "started" && event["phase"] !== "succeeded" && event["phase"] !== "failed" || !metadataText(event["operation"], 512) || !metadataText(event["stage"], 256) || "requestId" in event && !requestIdentifier(event["requestId"]) || "traceId" in event && !requestIdentifier(event["traceId"]) || "attempt" in event && (typeof event["attempt"] !== "number" || !Number.isInteger(event["attempt"]) || event["attempt"] < 1 || event["attempt"] > 1e6) || "durationMs" in event && (typeof event["durationMs"] !== "number" || !Number.isFinite(event["durationMs"]) || event["durationMs"] < 0 || event["durationMs"] > Number.MAX_SAFE_INTEGER))
|
|
15012
15032
|
return invalid();
|
|
15013
15033
|
return {
|
|
15014
|
-
kind: event
|
|
15015
|
-
operation: event
|
|
15016
|
-
stage: event
|
|
15017
|
-
phase: event
|
|
15018
|
-
...event
|
|
15019
|
-
...event
|
|
15020
|
-
...event
|
|
15021
|
-
...event
|
|
15034
|
+
kind: event["kind"],
|
|
15035
|
+
operation: event["operation"],
|
|
15036
|
+
stage: event["stage"],
|
|
15037
|
+
phase: event["phase"],
|
|
15038
|
+
...event["requestId"] === undefined ? {} : { requestId: event["requestId"] },
|
|
15039
|
+
...event["durationMs"] === undefined ? {} : { durationMs: event["durationMs"] },
|
|
15040
|
+
...event["attempt"] === undefined ? {} : { attempt: event["attempt"] },
|
|
15041
|
+
...event["traceId"] === undefined ? {} : { traceId: event["traceId"] }
|
|
15022
15042
|
};
|
|
15023
15043
|
});
|
|
15024
15044
|
if (Buffer.byteLength(JSON.stringify({ version: 1, events }), "utf8") > EXECUTION_CONTEXT_LIMITS.inputBytes)
|
|
@@ -15183,10 +15203,10 @@ function correlateSnapshot(snapshot, subject, events, requestId) {
|
|
|
15183
15203
|
correlation: "current-graph-only",
|
|
15184
15204
|
deploymentVerified: false,
|
|
15185
15205
|
eventsTrusted: false,
|
|
15186
|
-
modules: modules.slice(0, EXECUTION_CONTEXT_LIMITS.modules).map((module) =>
|
|
15187
|
-
|
|
15188
|
-
|
|
15189
|
-
})
|
|
15206
|
+
modules: modules.slice(0, EXECUTION_CONTEXT_LIMITS.modules).map((module) => {
|
|
15207
|
+
const file = executionSourceFile(module.file);
|
|
15208
|
+
return { name: module.name, ...file === undefined ? {} : { file } };
|
|
15209
|
+
}),
|
|
15190
15210
|
files: files.slice(0, EXECUTION_CONTEXT_LIMITS.files),
|
|
15191
15211
|
executionPlans: [...matchedPlans].slice(0, EXECUTION_CONTEXT_LIMITS.plans),
|
|
15192
15212
|
events: retained,
|
|
@@ -15434,10 +15454,11 @@ function createApplicationDevelopmentContext(graph, options = {}) {
|
|
|
15434
15454
|
const providers = bound(names(module.providers.map((provider) => provider.token)), moduleIndex < APPLICATION_DEVELOPMENT_LIMITS2.modules ? remainingProviders : 0);
|
|
15435
15455
|
remainingProviders -= providers.items.length;
|
|
15436
15456
|
omittedProviders += providers.omitted;
|
|
15457
|
+
const file = executionSourceFile(module.file);
|
|
15437
15458
|
developmentModules.push({
|
|
15438
15459
|
name: module.name,
|
|
15439
15460
|
className: module.className,
|
|
15440
|
-
...
|
|
15461
|
+
...file === undefined ? {} : { file },
|
|
15441
15462
|
...module.tags && module.tags.length > 0 ? { tags: names(module.tags) } : {},
|
|
15442
15463
|
providers: providers.items,
|
|
15443
15464
|
controllers: names(module.controllers.map((controller) => controller.className)),
|
|
@@ -15450,6 +15471,7 @@ function createApplicationDevelopmentContext(graph, options = {}) {
|
|
|
15450
15471
|
for (const route of controller.routes) {
|
|
15451
15472
|
const candidates = module.commands.filter((command) => command.className === route.command || command.name === route.command);
|
|
15452
15473
|
const command = candidates.length === 1 ? candidates[0]?.name : undefined;
|
|
15474
|
+
const kinds = schemaKinds(route);
|
|
15453
15475
|
routes.push({
|
|
15454
15476
|
module: module.name,
|
|
15455
15477
|
method: route.method,
|
|
@@ -15458,7 +15480,7 @@ function createApplicationDevelopmentContext(graph, options = {}) {
|
|
|
15458
15480
|
handler: route.handler,
|
|
15459
15481
|
...command === undefined ? {} : { command },
|
|
15460
15482
|
aspects: (route.aspects ?? []).map((aspect) => aspect.name),
|
|
15461
|
-
...
|
|
15483
|
+
...kinds === undefined ? {} : { schemaKinds: kinds }
|
|
15462
15484
|
});
|
|
15463
15485
|
}
|
|
15464
15486
|
}
|
|
@@ -15491,11 +15513,13 @@ function createApplicationDevelopmentContext(graph, options = {}) {
|
|
|
15491
15513
|
const diagnostics = [];
|
|
15492
15514
|
for (const diagnostic of graph.diagnostics ?? []) {
|
|
15493
15515
|
const repair = createDiagnosticRepairPlan([diagnostic])[0];
|
|
15516
|
+
const file = executionSourceFile(diagnostic.file);
|
|
15517
|
+
const line = Number.isSafeInteger(diagnostic.line) && diagnostic.line !== undefined && diagnostic.line > 0 ? diagnostic.line : undefined;
|
|
15494
15518
|
diagnostics.push({
|
|
15495
15519
|
code: diagnostic.code,
|
|
15496
15520
|
severity: diagnostic.severity,
|
|
15497
|
-
...
|
|
15498
|
-
...
|
|
15521
|
+
...file === undefined ? {} : { file },
|
|
15522
|
+
...line === undefined ? {} : { line },
|
|
15499
15523
|
...repair ? { repair: { type: repair.type, readiness: repair.readiness } } : {}
|
|
15500
15524
|
});
|
|
15501
15525
|
}
|
|
@@ -16185,16 +16209,16 @@ async function createDeliveryExecutionContextPack(manifestPath, target, subject,
|
|
|
16185
16209
|
if (!observations || typeof observations !== "object" || Array.isArray(observations))
|
|
16186
16210
|
throw invalid();
|
|
16187
16211
|
const envelope = observations;
|
|
16188
|
-
if (Object.keys(envelope).some((key) => !["version", "events", "delivery"].includes(key)) || !envelope
|
|
16212
|
+
if (Object.keys(envelope).some((key) => !["version", "events", "delivery"].includes(key)) || !envelope["delivery"] || typeof envelope["delivery"] !== "object" || Array.isArray(envelope["delivery"]))
|
|
16189
16213
|
throw invalid();
|
|
16190
|
-
const identity = envelope
|
|
16191
|
-
if (Object.keys(identity).length !== 2 || typeof identity
|
|
16214
|
+
const identity = envelope["delivery"];
|
|
16215
|
+
if (Object.keys(identity).length !== 2 || typeof identity["target"] !== "string" || typeof identity["objectId"] !== "string" || !/^[a-f0-9]{64}$/.test(identity["objectId"]))
|
|
16192
16216
|
throw invalid();
|
|
16193
16217
|
let object;
|
|
16194
16218
|
let snapshot;
|
|
16195
16219
|
try {
|
|
16196
16220
|
const { root, object: found, planned } = await readDeliverySelection(manifestPath, target);
|
|
16197
|
-
if (!found || identity
|
|
16221
|
+
if (!found || identity["target"] !== target || identity["objectId"] !== found.objectId) {
|
|
16198
16222
|
throw new DeliveryContextError("DELIVERY_CONTEXT_IDENTITY_MISMATCH");
|
|
16199
16223
|
}
|
|
16200
16224
|
object = found;
|
|
@@ -16211,7 +16235,7 @@ async function createDeliveryExecutionContextPack(manifestPath, target, subject,
|
|
|
16211
16235
|
throw new DeliveryContextError("DELIVERY_CONTEXT_INTEGRITY_FAILED");
|
|
16212
16236
|
}
|
|
16213
16237
|
const pack = {
|
|
16214
|
-
...executionContextFromSnapshot(snapshot, subject, { version: envelope
|
|
16238
|
+
...executionContextFromSnapshot(snapshot, subject, { version: envelope["version"], events: envelope["events"] }, requestId),
|
|
16215
16239
|
correlation: "verified-build-snapshot",
|
|
16216
16240
|
delivery: { target, objectId: object.objectId, artifactVerified: true }
|
|
16217
16241
|
};
|
|
@@ -16240,7 +16264,7 @@ var init_delivery_context = __esm(() => {
|
|
|
16240
16264
|
import { createHash as createHash9, randomUUID } from "node:crypto";
|
|
16241
16265
|
import { lstat as lstat2, readFile as readFile5, realpath as realpath3, rename as rename3, unlink as unlink2, writeFile as writeFile3 } from "node:fs/promises";
|
|
16242
16266
|
import { dirname as dirname8, isAbsolute as isAbsolute4, relative as relative9, resolve as resolve13, sep as sep9 } from "node:path";
|
|
16243
|
-
import * as
|
|
16267
|
+
import * as ts13 from "@typescript/typescript6";
|
|
16244
16268
|
async function applyDiagnosticFix(fix, options = {}) {
|
|
16245
16269
|
if (!fix || typeof fix.targetFile !== "string")
|
|
16246
16270
|
throw new Error("Invalid DiagnosticFix");
|
|
@@ -16269,7 +16293,7 @@ async function applyDiagnosticFix(fix, options = {}) {
|
|
|
16269
16293
|
if (!current || current.initializer.getText(source) !== fix.expectedExpression) {
|
|
16270
16294
|
throw new Error("Command mode changed since diagnosis; analyze the project again");
|
|
16271
16295
|
}
|
|
16272
|
-
content = replaceProperty(source, object, fix.property,
|
|
16296
|
+
content = replaceProperty(source, object, fix.property, ts13.factory.createStringLiteral(fix.value));
|
|
16273
16297
|
break;
|
|
16274
16298
|
}
|
|
16275
16299
|
case "add_module_import": {
|
|
@@ -16280,15 +16304,15 @@ async function applyDiagnosticFix(fix, options = {}) {
|
|
|
16280
16304
|
source = parse5(file, withImport);
|
|
16281
16305
|
const object = unique(moduleObjects(source).filter((candidate) => !fix.targetModule || stringProperty(candidate, "name") === fix.targetModule), "target module");
|
|
16282
16306
|
const imports = property(object, "imports");
|
|
16283
|
-
if (imports && !
|
|
16307
|
+
if (imports && !ts13.isArrayLiteralExpression(imports.initializer)) {
|
|
16284
16308
|
throw new Error("Module imports must be a static array");
|
|
16285
16309
|
}
|
|
16286
|
-
const values = imports &&
|
|
16287
|
-
if (values.some(
|
|
16310
|
+
const values = imports && ts13.isArrayLiteralExpression(imports.initializer) ? imports.initializer.elements : [];
|
|
16311
|
+
if (values.some(ts13.isSpreadElement))
|
|
16288
16312
|
throw new Error("Module imports cannot contain spread elements");
|
|
16289
|
-
content = values.some((value) =>
|
|
16313
|
+
content = values.some((value) => ts13.isIdentifier(value) && value.text === fix.symbol) ? withImport : replaceProperty(source, object, "imports", ts13.factory.createArrayLiteralExpression([
|
|
16290
16314
|
...values,
|
|
16291
|
-
|
|
16315
|
+
ts13.factory.createIdentifier(fix.symbol)
|
|
16292
16316
|
]));
|
|
16293
16317
|
break;
|
|
16294
16318
|
}
|
|
@@ -16300,24 +16324,24 @@ async function applyDiagnosticFix(fix, options = {}) {
|
|
|
16300
16324
|
const command = findClass(source, fix.command);
|
|
16301
16325
|
const object = decoratorObject(command, "Command");
|
|
16302
16326
|
const current = property(object, "permission");
|
|
16303
|
-
if (current && (!
|
|
16327
|
+
if (current && (!ts13.isStringLiteral(current.initializer) || current.initializer.text !== permission)) {
|
|
16304
16328
|
throw new Error("Command permission already exists with a different value");
|
|
16305
16329
|
}
|
|
16306
|
-
content = current ? original : replaceProperty(source, object, "permission",
|
|
16330
|
+
content = current ? original : replaceProperty(source, object, "permission", ts13.factory.createStringLiteral(permission));
|
|
16307
16331
|
break;
|
|
16308
16332
|
}
|
|
16309
16333
|
case "add_route_parameter_binding": {
|
|
16310
16334
|
const controller = findClass(source, fix.controller);
|
|
16311
|
-
const method = unique(controller.members.filter((member) =>
|
|
16312
|
-
const parameter = unique(method.parameters.filter((candidate) =>
|
|
16335
|
+
const method = unique(controller.members.filter((member) => ts13.isMethodDeclaration(member) && nameOf(member.name) === fix.route), "route handler");
|
|
16336
|
+
const parameter = unique(method.parameters.filter((candidate) => ts13.isIdentifier(candidate.name) && candidate.name.text === fix.parameter), "same-named route parameter");
|
|
16313
16337
|
const binding = fix.binding === "param" ? "Param" : fix.binding === "query" ? "Query" : undefined;
|
|
16314
16338
|
if (!binding)
|
|
16315
16339
|
throw new Error("Invalid route binding");
|
|
16316
|
-
const decorators =
|
|
16340
|
+
const decorators = ts13.getDecorators(parameter) ?? [];
|
|
16317
16341
|
if (decorators.length > 0)
|
|
16318
16342
|
throw new Error("Parameter already has a decorator");
|
|
16319
|
-
const framework = unique(source.statements.filter((statement) =>
|
|
16320
|
-
if (!
|
|
16343
|
+
const framework = unique(source.statements.filter((statement) => ts13.isImportDeclaration(statement) && statement.importClause?.namedBindings && ts13.isNamedImports(statement.importClause.namedBindings) && statement.importClause.namedBindings.elements.some((element) => ["Controller", "Get", "Post", "Put", "Patch", "Delete", "Head", "Options"].includes(element.name.text))), "framework import");
|
|
16344
|
+
if (!ts13.isImportDeclaration(framework) || !ts13.isStringLiteral(framework.moduleSpecifier)) {
|
|
16321
16345
|
throw new Error("Framework import must be static");
|
|
16322
16346
|
}
|
|
16323
16347
|
const edited = original.slice(0, parameter.getStart(source)) + `@${binding}(${JSON.stringify(fix.parameter)}) ` + original.slice(parameter.getStart(source));
|
|
@@ -16343,20 +16367,22 @@ async function applyDiagnosticFix(fix, options = {}) {
|
|
|
16343
16367
|
return result;
|
|
16344
16368
|
}
|
|
16345
16369
|
function parse5(file, text) {
|
|
16346
|
-
const result =
|
|
16370
|
+
const result = ts13.transpileModule(text, {
|
|
16347
16371
|
fileName: file,
|
|
16348
16372
|
reportDiagnostics: true,
|
|
16349
|
-
compilerOptions: { target:
|
|
16373
|
+
compilerOptions: { target: ts13.ScriptTarget.ESNext, experimentalDecorators: true }
|
|
16350
16374
|
});
|
|
16351
|
-
if (result.diagnostics?.some((item) => item.category ===
|
|
16375
|
+
if (result.diagnostics?.some((item) => item.category === ts13.DiagnosticCategory.Error)) {
|
|
16352
16376
|
throw new Error("Cannot fix syntactically invalid TypeScript");
|
|
16353
16377
|
}
|
|
16354
|
-
return
|
|
16378
|
+
return ts13.createSourceFile(file, text, ts13.ScriptTarget.Latest, true, ts13.ScriptKind.TS);
|
|
16355
16379
|
}
|
|
16356
16380
|
function unique(items, description) {
|
|
16357
|
-
|
|
16381
|
+
const [item] = items;
|
|
16382
|
+
if (items.length !== 1 || item === undefined) {
|
|
16358
16383
|
throw new Error(`Expected exactly one ${description}; found ${items.length}`);
|
|
16359
|
-
|
|
16384
|
+
}
|
|
16385
|
+
return item;
|
|
16360
16386
|
}
|
|
16361
16387
|
function identifier2(value) {
|
|
16362
16388
|
if (!/^[A-Za-z_$][\w$]*$/.test(value))
|
|
@@ -16365,50 +16391,50 @@ function identifier2(value) {
|
|
|
16365
16391
|
function nameOf(name) {
|
|
16366
16392
|
if (!name)
|
|
16367
16393
|
return "";
|
|
16368
|
-
return
|
|
16394
|
+
return ts13.isIdentifier(name) || ts13.isStringLiteral(name) || ts13.isNumericLiteral(name) ? name.text : "";
|
|
16369
16395
|
}
|
|
16370
16396
|
function property(object, key) {
|
|
16371
|
-
if (object.properties.some((item) => !
|
|
16397
|
+
if (object.properties.some((item) => !ts13.isPropertyAssignment(item) || ts13.isComputedPropertyName(item.name))) {
|
|
16372
16398
|
throw new Error("Fix requires explicit static object properties");
|
|
16373
16399
|
}
|
|
16374
|
-
const values = object.properties.filter((item) =>
|
|
16400
|
+
const values = object.properties.filter((item) => ts13.isPropertyAssignment(item) && nameOf(item.name) === key);
|
|
16375
16401
|
if (values.length > 1)
|
|
16376
16402
|
throw new Error(`Duplicate '${key}' property`);
|
|
16377
16403
|
return values[0];
|
|
16378
16404
|
}
|
|
16379
16405
|
function stringProperty(object, key) {
|
|
16380
16406
|
const value = property(object, key)?.initializer;
|
|
16381
|
-
return value &&
|
|
16407
|
+
return value && ts13.isStringLiteral(value) ? value.text : undefined;
|
|
16382
16408
|
}
|
|
16383
16409
|
function replaceProperty(source, object, key, value) {
|
|
16384
16410
|
const previous = property(object, key);
|
|
16385
|
-
const replacement =
|
|
16411
|
+
const replacement = ts13.factory.createPropertyAssignment(key, value);
|
|
16386
16412
|
const properties = object.properties.map((item) => item === previous ? replacement : item);
|
|
16387
16413
|
if (!previous)
|
|
16388
16414
|
properties.push(replacement);
|
|
16389
|
-
const updated =
|
|
16390
|
-
return source.text.slice(0, object.getStart(source)) +
|
|
16415
|
+
const updated = ts13.factory.updateObjectLiteralExpression(object, properties);
|
|
16416
|
+
return source.text.slice(0, object.getStart(source)) + ts13.createPrinter().printNode(ts13.EmitHint.Expression, updated, source) + source.text.slice(object.end);
|
|
16391
16417
|
}
|
|
16392
16418
|
function findClass(source, name) {
|
|
16393
|
-
return unique(source.statements.filter((statement) =>
|
|
16419
|
+
return unique(source.statements.filter((statement) => ts13.isClassDeclaration(statement) && statement.name?.text === name), `class '${name}'`);
|
|
16394
16420
|
}
|
|
16395
16421
|
function decoratorObject(node, name) {
|
|
16396
|
-
const decorator = unique((
|
|
16397
|
-
const argument =
|
|
16398
|
-
if (!argument || !
|
|
16422
|
+
const decorator = unique((ts13.getDecorators(node) ?? []).filter((item) => ts13.isCallExpression(item.expression) && item.expression.expression.getText() === name), `@${name} decorator`);
|
|
16423
|
+
const argument = ts13.isCallExpression(decorator.expression) ? decorator.expression.arguments[0] : undefined;
|
|
16424
|
+
if (!argument || !ts13.isObjectLiteralExpression(argument))
|
|
16399
16425
|
throw new Error(`@${name} requires a static object`);
|
|
16400
16426
|
return argument;
|
|
16401
16427
|
}
|
|
16402
16428
|
function moduleObjects(source) {
|
|
16403
16429
|
const result = [];
|
|
16404
16430
|
for (const statement of source.statements) {
|
|
16405
|
-
if (
|
|
16431
|
+
if (ts13.isClassDeclaration(statement) && (ts13.getDecorators(statement) ?? []).some((item) => ts13.isCallExpression(item.expression) && item.expression.expression.getText() === "Module")) {
|
|
16406
16432
|
result.push(decoratorObject(statement, "Module"));
|
|
16407
16433
|
}
|
|
16408
|
-
if (
|
|
16434
|
+
if (ts13.isVariableStatement(statement)) {
|
|
16409
16435
|
for (const declaration of statement.declarationList.declarations) {
|
|
16410
16436
|
const call = declaration.initializer;
|
|
16411
|
-
if (call &&
|
|
16437
|
+
if (call && ts13.isCallExpression(call) && ["defineModule", "defineFeatureSlice"].includes(call.expression.getText()) && call.arguments[0] && ts13.isObjectLiteralExpression(call.arguments[0])) {
|
|
16412
16438
|
result.push(call.arguments[0]);
|
|
16413
16439
|
}
|
|
16414
16440
|
}
|
|
@@ -16422,19 +16448,19 @@ function importSymbol(source, path, symbol) {
|
|
|
16422
16448
|
const target = resolve13(dirname8(source.fileName), path).replace(/\.(tsx?|mts|cts)$/, "");
|
|
16423
16449
|
if (current === target)
|
|
16424
16450
|
return source.text;
|
|
16425
|
-
const matches = source.statements.filter((item) =>
|
|
16451
|
+
const matches = source.statements.filter((item) => ts13.isImportDeclaration(item) && ts13.isStringLiteral(item.moduleSpecifier) && item.moduleSpecifier.text === path);
|
|
16426
16452
|
if (matches.length > 1)
|
|
16427
16453
|
throw new Error(`Ambiguous imports from '${path}'`);
|
|
16428
16454
|
const match = matches[0];
|
|
16429
|
-
if (match &&
|
|
16455
|
+
if (match && ts13.isImportDeclaration(match) && match.importClause?.namedBindings && ts13.isNamedImports(match.importClause.namedBindings) && !match.importClause.isTypeOnly) {
|
|
16430
16456
|
if (match.importClause.namedBindings.elements.some((item) => item.name.text === symbol))
|
|
16431
16457
|
return source.text;
|
|
16432
16458
|
const bindings = match.importClause.namedBindings;
|
|
16433
|
-
const updated =
|
|
16459
|
+
const updated = ts13.factory.updateNamedImports(bindings, [
|
|
16434
16460
|
...bindings.elements,
|
|
16435
|
-
|
|
16461
|
+
ts13.factory.createImportSpecifier(false, undefined, ts13.factory.createIdentifier(symbol))
|
|
16436
16462
|
]);
|
|
16437
|
-
return source.text.slice(0, bindings.getStart(source)) +
|
|
16463
|
+
return source.text.slice(0, bindings.getStart(source)) + ts13.createPrinter().printNode(ts13.EmitHint.Unspecified, updated, source) + source.text.slice(bindings.end);
|
|
16438
16464
|
}
|
|
16439
16465
|
if (match)
|
|
16440
16466
|
throw new Error(`Import from '${path}' is not a named value import`);
|
|
@@ -16541,7 +16567,7 @@ var init_application_configuration = __esm(() => {
|
|
|
16541
16567
|
});
|
|
16542
16568
|
|
|
16543
16569
|
// node_modules/@supacloud/delivery/src/application-activation.ts
|
|
16544
|
-
var ApplicationActivationIdSchema, ApplicationActivationWriteSchema, ApplicationActivationResultSchema, ApplicationActivationRetirementResultSchema;
|
|
16570
|
+
var ApplicationActivationIdSchema, ApplicationActivationWriteSchema, ApplicationActivationResultSchema, ApplicationActivationRetirementResultSchema, RollbackActivationSchema, ApplicationRollbackSnapshotSchema;
|
|
16545
16571
|
var init_application_activation = __esm(() => {
|
|
16546
16572
|
init_build();
|
|
16547
16573
|
init_application_configuration();
|
|
@@ -16568,16 +16594,261 @@ var init_application_activation = __esm(() => {
|
|
|
16568
16594
|
activation_id: ApplicationActivationIdSchema,
|
|
16569
16595
|
retired_at: String2()
|
|
16570
16596
|
}, { additionalProperties: false });
|
|
16597
|
+
RollbackActivationSchema = _Object_({
|
|
16598
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16599
|
+
configuration_id: ApplicationConfigurationIdSchema,
|
|
16600
|
+
activation_id: ApplicationActivationIdSchema
|
|
16601
|
+
}, { additionalProperties: false });
|
|
16602
|
+
ApplicationRollbackSnapshotSchema = _Object_({
|
|
16603
|
+
schema: Literal("supacloud.application-rollback-snapshot.v1"),
|
|
16604
|
+
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16605
|
+
application_id: ApplicationIdSchema,
|
|
16606
|
+
environment_id: ApplicationIdSchema,
|
|
16607
|
+
active: Union([RollbackActivationSchema, Null()]),
|
|
16608
|
+
previous: Union([RollbackActivationSchema, Null()])
|
|
16609
|
+
}, { additionalProperties: false });
|
|
16610
|
+
});
|
|
16611
|
+
|
|
16612
|
+
// node_modules/@supacloud/delivery/src/application-deploy-plan.ts
|
|
16613
|
+
var CandidateSchema, ApplicationDeployPlanSchema;
|
|
16614
|
+
var init_application_deploy_plan = __esm(() => {
|
|
16615
|
+
init_build();
|
|
16616
|
+
init_value2();
|
|
16617
|
+
init_application_release();
|
|
16618
|
+
init_application_activation();
|
|
16619
|
+
init_application_configuration();
|
|
16620
|
+
CandidateSchema = _Object_({
|
|
16621
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16622
|
+
configuration_id: ApplicationConfigurationIdSchema
|
|
16623
|
+
}, { additionalProperties: false });
|
|
16624
|
+
ApplicationDeployPlanSchema = _Object_({
|
|
16625
|
+
schema: Literal("supacloud.application-deploy-plan.v1"),
|
|
16626
|
+
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16627
|
+
application_id: ApplicationIdSchema,
|
|
16628
|
+
environment_id: ApplicationIdSchema,
|
|
16629
|
+
candidate: CandidateSchema,
|
|
16630
|
+
current: Union([_Object_({
|
|
16631
|
+
...CandidateSchema.properties,
|
|
16632
|
+
activation_id: ApplicationActivationIdSchema
|
|
16633
|
+
}, { additionalProperties: false }), Null()]),
|
|
16634
|
+
expected_activation_id: Union([ApplicationActivationIdSchema, Null()]),
|
|
16635
|
+
action: Union([Literal("activate"), Literal("no-op")]),
|
|
16636
|
+
changes: _Object_({
|
|
16637
|
+
release: Boolean2(),
|
|
16638
|
+
configuration: Boolean2(),
|
|
16639
|
+
targets: _Object_({
|
|
16640
|
+
added: _Array_(String2()),
|
|
16641
|
+
removed: _Array_(String2()),
|
|
16642
|
+
changed: _Array_(String2())
|
|
16643
|
+
}, { additionalProperties: false })
|
|
16644
|
+
}, { additionalProperties: false }),
|
|
16645
|
+
migrations: _Object_({
|
|
16646
|
+
ledger_digest: ApplicationReleaseIdSchema,
|
|
16647
|
+
ledger_compatible: Boolean2(),
|
|
16648
|
+
project_migrations_applied: Boolean2(),
|
|
16649
|
+
operator_provisioning: Union([
|
|
16650
|
+
Literal("separate-verification-required"),
|
|
16651
|
+
Literal("not-declared")
|
|
16652
|
+
])
|
|
16653
|
+
}, { additionalProperties: false }),
|
|
16654
|
+
compatibility: Literal("not-proven"),
|
|
16655
|
+
execution_performed: Literal(false)
|
|
16656
|
+
}, { additionalProperties: false });
|
|
16657
|
+
});
|
|
16658
|
+
|
|
16659
|
+
// node_modules/@supacloud/delivery/src/application-release-operation.ts
|
|
16660
|
+
var closed6, nullableActivation, ApplicationReleaseRequestSchema, ApplicationReleaseResultSchema;
|
|
16661
|
+
var init_application_release_operation = __esm(() => {
|
|
16662
|
+
init_build();
|
|
16663
|
+
init_value2();
|
|
16664
|
+
init_application_activation();
|
|
16665
|
+
init_application_configuration();
|
|
16666
|
+
init_application_release();
|
|
16667
|
+
closed6 = { additionalProperties: false };
|
|
16668
|
+
nullableActivation = Union([ApplicationActivationIdSchema, Null()]);
|
|
16669
|
+
ApplicationReleaseRequestSchema = _Object_({
|
|
16670
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16671
|
+
configuration_id: Optional(ApplicationConfigurationIdSchema),
|
|
16672
|
+
configuration_write: Optional(ApplicationConfigurationWriteSchema),
|
|
16673
|
+
activation_id: Optional(ApplicationActivationIdSchema),
|
|
16674
|
+
expected_activation_id: Optional(nullableActivation),
|
|
16675
|
+
expected_plan_sha256: Optional(ApplicationReleaseIdSchema)
|
|
16676
|
+
}, closed6);
|
|
16677
|
+
ApplicationReleaseResultSchema = _Object_({
|
|
16678
|
+
schema: Literal("supacloud.application-release.v1"),
|
|
16679
|
+
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16680
|
+
application_id: ApplicationIdSchema,
|
|
16681
|
+
environment_id: ApplicationIdSchema,
|
|
16682
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16683
|
+
configuration_id: ApplicationConfigurationIdSchema,
|
|
16684
|
+
activation_id: ApplicationActivationIdSchema,
|
|
16685
|
+
expected_activation_id: nullableActivation,
|
|
16686
|
+
plan_sha256: ApplicationReleaseIdSchema,
|
|
16687
|
+
action: Union([Literal("activate"), Literal("no-op")]),
|
|
16688
|
+
replayed: Boolean2(),
|
|
16689
|
+
execution_performed: Boolean2()
|
|
16690
|
+
}, closed6);
|
|
16691
|
+
});
|
|
16692
|
+
|
|
16693
|
+
// node_modules/@supacloud/delivery/src/application-history.ts
|
|
16694
|
+
var scope, timestamp, ApplicationActivationHistoryPositionSchema, cursorSchema, ApplicationActivationHistoryCursorSchema, entrySchema, ApplicationActivationHistorySchema;
|
|
16695
|
+
var init_application_history = __esm(() => {
|
|
16696
|
+
init_build();
|
|
16697
|
+
init_value2();
|
|
16698
|
+
init_application_activation();
|
|
16699
|
+
init_application_configuration();
|
|
16700
|
+
init_application_release();
|
|
16701
|
+
scope = {
|
|
16702
|
+
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16703
|
+
application_id: ApplicationIdSchema,
|
|
16704
|
+
environment_id: ApplicationIdSchema
|
|
16705
|
+
};
|
|
16706
|
+
timestamp = String2({ pattern: "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}\\.\\d{6}Z$" });
|
|
16707
|
+
ApplicationActivationHistoryPositionSchema = _Object_({
|
|
16708
|
+
completed_at: timestamp,
|
|
16709
|
+
activation_id: ApplicationActivationIdSchema
|
|
16710
|
+
}, { additionalProperties: false });
|
|
16711
|
+
cursorSchema = _Object_({
|
|
16712
|
+
...scope,
|
|
16713
|
+
...ApplicationActivationHistoryPositionSchema.properties
|
|
16714
|
+
}, { additionalProperties: false });
|
|
16715
|
+
ApplicationActivationHistoryCursorSchema = String2({
|
|
16716
|
+
pattern: "^[A-Za-z0-9_-]+$",
|
|
16717
|
+
maxLength: 1024,
|
|
16718
|
+
minLength: 1
|
|
16719
|
+
});
|
|
16720
|
+
entrySchema = _Object_({
|
|
16721
|
+
...ApplicationActivationHistoryPositionSchema.properties,
|
|
16722
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16723
|
+
configuration_id: Union([ApplicationConfigurationIdSchema, Null()]),
|
|
16724
|
+
previous_activation_id: Union([ApplicationActivationIdSchema, Null()]),
|
|
16725
|
+
is_active: Boolean2()
|
|
16726
|
+
}, { additionalProperties: false });
|
|
16727
|
+
ApplicationActivationHistorySchema = _Object_({
|
|
16728
|
+
schema: Literal("supacloud.application-activation-history.v1"),
|
|
16729
|
+
...scope,
|
|
16730
|
+
active_activation_id: Union([ApplicationActivationIdSchema, Null()]),
|
|
16731
|
+
activations: _Array_(entrySchema, { maxItems: 100 }),
|
|
16732
|
+
next_cursor: Union([ApplicationActivationHistoryCursorSchema, Null()])
|
|
16733
|
+
}, { additionalProperties: false });
|
|
16734
|
+
});
|
|
16735
|
+
|
|
16736
|
+
// node_modules/@supacloud/delivery/src/application-preview.ts
|
|
16737
|
+
var phaseStatus, closed7, ApplicationPreviewReceiptSchema;
|
|
16738
|
+
var init_application_preview = __esm(() => {
|
|
16739
|
+
init_build();
|
|
16740
|
+
init_value2();
|
|
16741
|
+
init_application_configuration();
|
|
16742
|
+
init_application_activation();
|
|
16743
|
+
init_application_release();
|
|
16744
|
+
phaseStatus = Union([
|
|
16745
|
+
Literal("pending"),
|
|
16746
|
+
Literal("ready"),
|
|
16747
|
+
Literal("failed"),
|
|
16748
|
+
Literal("cleaned")
|
|
16749
|
+
]);
|
|
16750
|
+
closed7 = { additionalProperties: false };
|
|
16751
|
+
ApplicationPreviewReceiptSchema = _Object_({
|
|
16752
|
+
schema: Literal("supacloud.application-preview.v1"),
|
|
16753
|
+
preview_id: String2({ pattern: "^[a-f0-9-]{8,64}$" }),
|
|
16754
|
+
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16755
|
+
application_id: ApplicationIdSchema,
|
|
16756
|
+
environment_id: ApplicationIdSchema,
|
|
16757
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16758
|
+
expires_at: Optional(Union([String2({
|
|
16759
|
+
pattern: "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}\\.\\d{3}Z$",
|
|
16760
|
+
maxLength: 24
|
|
16761
|
+
}), Null()])),
|
|
16762
|
+
status: Union([
|
|
16763
|
+
Literal("planned"),
|
|
16764
|
+
Literal("provisioning"),
|
|
16765
|
+
Literal("ready"),
|
|
16766
|
+
Literal("failed"),
|
|
16767
|
+
Literal("cleaned")
|
|
16768
|
+
]),
|
|
16769
|
+
resources: _Object_({
|
|
16770
|
+
build_artifact: _Object_({ status: phaseStatus, release_id: ApplicationReleaseIdSchema }, closed7),
|
|
16771
|
+
database_branch: _Object_({
|
|
16772
|
+
status: phaseStatus,
|
|
16773
|
+
branch_ref: String2({ pattern: "^[A-Za-z0-9_-]{1,20}$" }),
|
|
16774
|
+
data_mode: Union([Literal("schema_only"), Literal("full_clone")])
|
|
16775
|
+
}, closed7),
|
|
16776
|
+
queue_namespace: _Object_({
|
|
16777
|
+
status: phaseStatus,
|
|
16778
|
+
namespace: String2({ minLength: 1, maxLength: 128 })
|
|
16779
|
+
}, closed7),
|
|
16780
|
+
storage_namespace: _Object_({
|
|
16781
|
+
status: phaseStatus,
|
|
16782
|
+
namespace: String2({ minLength: 1, maxLength: 128 })
|
|
16783
|
+
}, closed7),
|
|
16784
|
+
test_secret: _Object_({
|
|
16785
|
+
status: phaseStatus,
|
|
16786
|
+
name: String2({ minLength: 1, maxLength: 128 }),
|
|
16787
|
+
value_issued: Literal(false)
|
|
16788
|
+
}, closed7),
|
|
16789
|
+
configuration_revision: _Object_({
|
|
16790
|
+
status: phaseStatus,
|
|
16791
|
+
configuration_id: Union([ApplicationConfigurationIdSchema, Null()])
|
|
16792
|
+
}, closed7),
|
|
16793
|
+
application_activation: _Object_({
|
|
16794
|
+
status: phaseStatus,
|
|
16795
|
+
activation_id: Union([ApplicationActivationIdSchema, Null()])
|
|
16796
|
+
}, closed7),
|
|
16797
|
+
smoke_test: _Object_({
|
|
16798
|
+
status: phaseStatus,
|
|
16799
|
+
checks: _Array_(String2({ minLength: 1, maxLength: 64 }), { maxItems: 32 }),
|
|
16800
|
+
passed: _Array_(String2({ minLength: 1, maxLength: 64 }), { maxItems: 32 }),
|
|
16801
|
+
failed: _Array_(String2({ minLength: 1, maxLength: 64 }), { maxItems: 32 })
|
|
16802
|
+
}, closed7)
|
|
16803
|
+
}, closed7),
|
|
16804
|
+
cleanup: _Object_({
|
|
16805
|
+
required: Boolean2(),
|
|
16806
|
+
completed: Boolean2(),
|
|
16807
|
+
error: Union([String2({ minLength: 1, maxLength: 128 }), Null()])
|
|
16808
|
+
}, closed7)
|
|
16809
|
+
}, closed7);
|
|
16810
|
+
});
|
|
16811
|
+
|
|
16812
|
+
// node_modules/@supacloud/delivery/src/application-release-transfer.ts
|
|
16813
|
+
var projectRef, source, identity, ApplicationReleaseTransferPlanSchema, ApplicationReleaseTransferResultSchema;
|
|
16814
|
+
var init_application_release_transfer = __esm(() => {
|
|
16815
|
+
init_build();
|
|
16816
|
+
init_value2();
|
|
16817
|
+
init_application_release();
|
|
16818
|
+
projectRef = String2({ pattern: "^[A-Za-z0-9_-]{1,20}$" });
|
|
16819
|
+
source = _Object_({
|
|
16820
|
+
project_ref: projectRef,
|
|
16821
|
+
release_id: ApplicationReleaseIdSchema,
|
|
16822
|
+
manifest_sha256: ApplicationReleaseIdSchema
|
|
16823
|
+
}, { additionalProperties: false });
|
|
16824
|
+
identity = {
|
|
16825
|
+
project_ref: projectRef,
|
|
16826
|
+
application_id: ApplicationIdSchema,
|
|
16827
|
+
source,
|
|
16828
|
+
candidate_release_id: ApplicationReleaseIdSchema
|
|
16829
|
+
};
|
|
16830
|
+
ApplicationReleaseTransferPlanSchema = _Object_({
|
|
16831
|
+
schema: Literal("supacloud.application-release-transfer-plan.v1"),
|
|
16832
|
+
...identity,
|
|
16833
|
+
action: Union([Literal("materialize"), Literal("no-op")]),
|
|
16834
|
+
execution_performed: Literal(false)
|
|
16835
|
+
}, { additionalProperties: false });
|
|
16836
|
+
ApplicationReleaseTransferResultSchema = _Object_({
|
|
16837
|
+
schema: Literal("supacloud.application-release-transfer-result.v1"),
|
|
16838
|
+
...identity,
|
|
16839
|
+
release: ApplicationReleaseRecordSchema,
|
|
16840
|
+
activation_performed: Literal(false)
|
|
16841
|
+
}, { additionalProperties: false });
|
|
16571
16842
|
});
|
|
16572
16843
|
|
|
16573
16844
|
// node_modules/@supacloud/delivery/src/deployment-evidence.ts
|
|
16574
|
-
var
|
|
16845
|
+
var closed8, sha256, isoDate, status, evidenceStatus, DEPLOYMENT_EVIDENCE_SCHEMA = "supacloud.deployment-evidence.v1", DatabaseProviderSchema, componentName, DeploymentComponentEvidenceSchema, DeploymentEvidenceSchema;
|
|
16575
16846
|
var init_deployment_evidence = __esm(() => {
|
|
16576
16847
|
init_build();
|
|
16577
16848
|
init_value2();
|
|
16578
16849
|
init_application_configuration();
|
|
16579
16850
|
init_application_release();
|
|
16580
|
-
|
|
16851
|
+
closed8 = { additionalProperties: false };
|
|
16581
16852
|
sha256 = String2({ pattern: "^[a-f0-9]{64}$" });
|
|
16582
16853
|
isoDate = String2({ minLength: 20, maxLength: 40 });
|
|
16583
16854
|
status = Union([
|
|
@@ -16603,19 +16874,19 @@ var init_deployment_evidence = __esm(() => {
|
|
|
16603
16874
|
Literal("not-proven"),
|
|
16604
16875
|
Literal("failed")
|
|
16605
16876
|
])
|
|
16606
|
-
},
|
|
16877
|
+
}, closed8),
|
|
16607
16878
|
backup: _Object_({
|
|
16608
16879
|
status,
|
|
16609
16880
|
latest_success_at: Union([isoDate, Null()]),
|
|
16610
16881
|
freshness_seconds: Union([Integer({ minimum: 0 }), Null()])
|
|
16611
|
-
},
|
|
16882
|
+
}, closed8),
|
|
16612
16883
|
recovery: _Object_({
|
|
16613
16884
|
status,
|
|
16614
16885
|
drill_id: Union([String2({ minLength: 1, maxLength: 128 }), Null()]),
|
|
16615
16886
|
rpo_seconds: Union([Integer({ minimum: 0 }), Null()]),
|
|
16616
16887
|
rto_seconds: Union([Integer({ minimum: 0 }), Null()])
|
|
16617
|
-
},
|
|
16618
|
-
},
|
|
16888
|
+
}, closed8)
|
|
16889
|
+
}, closed8);
|
|
16619
16890
|
componentName = Union([
|
|
16620
16891
|
Literal("management-api"),
|
|
16621
16892
|
Literal("web-console"),
|
|
@@ -16633,7 +16904,7 @@ var init_deployment_evidence = __esm(() => {
|
|
|
16633
16904
|
status,
|
|
16634
16905
|
health_check: Union([String2({ minLength: 1, maxLength: 256 }), Null()]),
|
|
16635
16906
|
checked_at: Union([isoDate, Null()])
|
|
16636
|
-
},
|
|
16907
|
+
}, closed8);
|
|
16637
16908
|
DeploymentEvidenceSchema = _Object_({
|
|
16638
16909
|
schema: Literal(DEPLOYMENT_EVIDENCE_SCHEMA),
|
|
16639
16910
|
status: evidenceStatus,
|
|
@@ -16642,33 +16913,110 @@ var init_deployment_evidence = __esm(() => {
|
|
|
16642
16913
|
project_ref: String2({ pattern: "^[a-z0-9-]{1,20}$" }),
|
|
16643
16914
|
application_id: ApplicationIdSchema,
|
|
16644
16915
|
environment_id: ApplicationIdSchema
|
|
16645
|
-
},
|
|
16916
|
+
}, closed8),
|
|
16646
16917
|
source: _Object_({
|
|
16647
16918
|
commit_sha: Union([String2({ pattern: "^[0-9a-f]{7,64}$" }), Null()]),
|
|
16648
16919
|
manifest_sha256: sha256,
|
|
16649
16920
|
contract_schema: Union([String2({ minLength: 1, maxLength: 128 }), Null()]),
|
|
16650
16921
|
environment_binding_version: Union([sha256, Null()])
|
|
16651
|
-
},
|
|
16922
|
+
}, closed8),
|
|
16652
16923
|
database: DatabaseProviderSchema,
|
|
16653
16924
|
components: _Array_(DeploymentComponentEvidenceSchema, { minItems: 1, maxItems: 32 }),
|
|
16654
16925
|
activation: _Object_({
|
|
16655
16926
|
release_id: ApplicationReleaseIdSchema,
|
|
16656
16927
|
configuration_id: ApplicationConfigurationIdSchema,
|
|
16657
16928
|
activation_id: ApplicationConfigurationIdSchema
|
|
16658
|
-
},
|
|
16929
|
+
}, closed8),
|
|
16659
16930
|
health: _Object_({
|
|
16660
16931
|
status,
|
|
16661
16932
|
checked_at: Union([isoDate, Null()]),
|
|
16662
16933
|
authenticated_smoke: status
|
|
16663
|
-
},
|
|
16934
|
+
}, closed8),
|
|
16664
16935
|
rollback: _Object_({
|
|
16665
16936
|
release_id: Union([ApplicationReleaseIdSchema, Null()]),
|
|
16666
16937
|
configuration_id: Union([ApplicationConfigurationIdSchema, Null()]),
|
|
16667
16938
|
status: Union([Literal("ready"), Literal("not-ready"), Literal("unknown")]),
|
|
16668
16939
|
result: Union([status, Null()])
|
|
16669
|
-
},
|
|
16940
|
+
}, closed8),
|
|
16670
16941
|
notes: _Array_(String2({ minLength: 1, maxLength: 512 }), { maxItems: 32 })
|
|
16671
|
-
},
|
|
16942
|
+
}, closed8);
|
|
16943
|
+
});
|
|
16944
|
+
|
|
16945
|
+
// node_modules/@supacloud/delivery/src/application-promotion.ts
|
|
16946
|
+
var closed9, projectRef2, sha2562, nullableActivation2, nullableDigest, observation, blocker, ApplicationPromotionPlanSchema;
|
|
16947
|
+
var init_application_promotion = __esm(() => {
|
|
16948
|
+
init_build();
|
|
16949
|
+
init_value2();
|
|
16950
|
+
init_delivery_files();
|
|
16951
|
+
init_application_activation();
|
|
16952
|
+
init_application_configuration();
|
|
16953
|
+
init_application_release();
|
|
16954
|
+
closed9 = { additionalProperties: false };
|
|
16955
|
+
projectRef2 = String2({ pattern: "^[a-z0-9-]{1,20}$" });
|
|
16956
|
+
sha2562 = ApplicationReleaseIdSchema;
|
|
16957
|
+
nullableActivation2 = Union([ApplicationActivationIdSchema, Null()]);
|
|
16958
|
+
nullableDigest = Union([sha2562, Null()]);
|
|
16959
|
+
observation = {
|
|
16960
|
+
activation_id: nullableActivation2,
|
|
16961
|
+
receipt_confirmed: Boolean2(),
|
|
16962
|
+
ready: Boolean2(),
|
|
16963
|
+
smoke_verified: Boolean2(),
|
|
16964
|
+
evidence_sha256: nullableDigest,
|
|
16965
|
+
migration_ledger_digest: nullableDigest
|
|
16966
|
+
};
|
|
16967
|
+
blocker = [
|
|
16968
|
+
"SOURCE_NOT_ACTIVE",
|
|
16969
|
+
"SOURCE_RECEIPT_UNCONFIRMED",
|
|
16970
|
+
"SOURCE_NOT_READY",
|
|
16971
|
+
"SOURCE_SMOKE_UNVERIFIED",
|
|
16972
|
+
"TARGET_CONFIGURATION_MISSING",
|
|
16973
|
+
"TARGET_CONFIGURATION_MISMATCH",
|
|
16974
|
+
"MIGRATION_PENDING",
|
|
16975
|
+
"MIGRATION_CONFLICT",
|
|
16976
|
+
"OPERATOR_PROVISIONING_REQUIRED",
|
|
16977
|
+
"BACKUP_REQUIRED"
|
|
16978
|
+
];
|
|
16979
|
+
ApplicationPromotionPlanSchema = _Object_({
|
|
16980
|
+
schema: Literal("supacloud.application-promotion-plan.v1"),
|
|
16981
|
+
project_ref: projectRef2,
|
|
16982
|
+
application_id: ApplicationIdSchema,
|
|
16983
|
+
environment_id: ApplicationIdSchema,
|
|
16984
|
+
manifest_sha256: sha2562,
|
|
16985
|
+
plan_sha256: sha2562,
|
|
16986
|
+
source: _Object_({
|
|
16987
|
+
project_ref: projectRef2,
|
|
16988
|
+
environment_id: ApplicationIdSchema,
|
|
16989
|
+
release_id: sha2562,
|
|
16990
|
+
...observation
|
|
16991
|
+
}, closed9),
|
|
16992
|
+
target: _Object_({
|
|
16993
|
+
candidate_release_id: sha2562,
|
|
16994
|
+
current_release_id: Union([sha2562, Null()]),
|
|
16995
|
+
artifact_action: Union([Literal("materialize"), Literal("reuse")]),
|
|
16996
|
+
configuration_id: Union([ApplicationConfigurationIdSchema, Null()]),
|
|
16997
|
+
configuration: Union([ApplicationConfigurationViewSchema, Null()]),
|
|
16998
|
+
...observation
|
|
16999
|
+
}, closed9),
|
|
17000
|
+
migrations: _Object_({
|
|
17001
|
+
ledger_digest: sha2562,
|
|
17002
|
+
ledger_compatible: Boolean2(),
|
|
17003
|
+
project_migrations_applied: Boolean2(),
|
|
17004
|
+
pending_versions: _Array_(String2({ pattern: "^\\d{1,20}$" }), { maxItems: 4096, uniqueItems: true }),
|
|
17005
|
+
operator_provisioning_required: Boolean2()
|
|
17006
|
+
}, closed9),
|
|
17007
|
+
backup: _Object_({
|
|
17008
|
+
required: Boolean2(),
|
|
17009
|
+
confirmed: Literal(false)
|
|
17010
|
+
}, closed9),
|
|
17011
|
+
action: Union([Literal("promote"), Literal("no-op"), Literal("blocked")]),
|
|
17012
|
+
blockers: _Array_(Enum([...blocker]), {
|
|
17013
|
+
maxItems: blocker.length,
|
|
17014
|
+
uniqueItems: true
|
|
17015
|
+
}),
|
|
17016
|
+
steps: _Array_(String2({ minLength: 1, maxLength: 64 }), { maxItems: 8, uniqueItems: true }),
|
|
17017
|
+
execution_performed: Literal(false),
|
|
17018
|
+
data_recovery: Literal("separate-required")
|
|
17019
|
+
}, closed9);
|
|
16672
17020
|
});
|
|
16673
17021
|
|
|
16674
17022
|
// node_modules/@supacloud/delivery/src/application-runtime-identity.ts
|
|
@@ -16759,13 +17107,13 @@ async function readDeliveryMigrationArchive(manifestPath, target) {
|
|
|
16759
17107
|
throw new Error("Invalid delivery migration archive.");
|
|
16760
17108
|
}
|
|
16761
17109
|
}
|
|
16762
|
-
var
|
|
17110
|
+
var entrySchema2, archiveSchema;
|
|
16763
17111
|
var init_delivery_migration_archive = __esm(() => {
|
|
16764
17112
|
init_build();
|
|
16765
17113
|
init_value2();
|
|
16766
17114
|
init_delivery_artifact();
|
|
16767
17115
|
init_delivery_files();
|
|
16768
|
-
|
|
17116
|
+
entrySchema2 = _Object_({
|
|
16769
17117
|
version: String2({ pattern: "^[1-9][0-9]{0,18}$" }),
|
|
16770
17118
|
name: String2({ pattern: "^[A-Za-z][A-Za-z0-9_-]{0,127}$" }),
|
|
16771
17119
|
executor: Union([Literal("project-migration"), Literal("operator-provisioning")]),
|
|
@@ -16779,7 +17127,7 @@ var init_delivery_migration_archive = __esm(() => {
|
|
|
16779
17127
|
compatibility: Literal("not-proven"),
|
|
16780
17128
|
executionPerformed: Literal(false),
|
|
16781
17129
|
dataRecovery: Literal("separate-required"),
|
|
16782
|
-
migrations: _Array_(
|
|
17130
|
+
migrations: _Array_(entrySchema2, { minItems: 1, maxItems: 128 })
|
|
16783
17131
|
}, { additionalProperties: false });
|
|
16784
17132
|
});
|
|
16785
17133
|
|
|
@@ -16792,9 +17140,15 @@ var init_src = __esm(() => {
|
|
|
16792
17140
|
init_worker_execution();
|
|
16793
17141
|
init_worker_execution();
|
|
16794
17142
|
init_application_activation();
|
|
17143
|
+
init_application_deploy_plan();
|
|
17144
|
+
init_application_release_operation();
|
|
17145
|
+
init_application_history();
|
|
16795
17146
|
init_application_release();
|
|
17147
|
+
init_application_preview();
|
|
17148
|
+
init_application_release_transfer();
|
|
16796
17149
|
init_application_configuration();
|
|
16797
17150
|
init_deployment_evidence();
|
|
17151
|
+
init_application_promotion();
|
|
16798
17152
|
init_application_runtime_identity();
|
|
16799
17153
|
init_delivery_build_schema();
|
|
16800
17154
|
init_delivery_migration_archive();
|
|
@@ -16956,7 +17310,7 @@ var init_release_evidence_cli = __esm(() => {
|
|
|
16956
17310
|
import { createHash as createHash12 } from "node:crypto";
|
|
16957
17311
|
import { mkdir as mkdir5, readFile as readFile13 } from "node:fs/promises";
|
|
16958
17312
|
import { dirname as dirname11, relative as relative12, resolve as resolve23 } from "node:path";
|
|
16959
|
-
import * as
|
|
17313
|
+
import * as ts18 from "@typescript/typescript6";
|
|
16960
17314
|
function hash3(value) {
|
|
16961
17315
|
return createHash12("sha256").update(value).digest("hex");
|
|
16962
17316
|
}
|
|
@@ -16996,20 +17350,20 @@ async function generateDatabaseContracts(options, check = false) {
|
|
|
16996
17350
|
const rootDir = resolve23(options.rootDir), outDir = resolve23(options.outDir);
|
|
16997
17351
|
const postgrestTypes = resolve23(rootDir, options.postgrestTypes), drizzleSchema = resolve23(rootDir, options.drizzleSchema);
|
|
16998
17352
|
const snapshot = await readFile13(postgrestTypes, "utf8");
|
|
16999
|
-
const syntax =
|
|
17000
|
-
const database = syntax.statements.find((node) => (
|
|
17353
|
+
const syntax = ts18.createSourceFile(postgrestTypes, snapshot, ts18.ScriptTarget.Latest, true);
|
|
17354
|
+
const database = syntax.statements.find((node) => (ts18.isTypeAliasDeclaration(node) || ts18.isInterfaceDeclaration(node)) && node.name.text === "Database" && node.modifiers?.some((modifier) => modifier.kind === ts18.SyntaxKind.ExportKeyword));
|
|
17001
17355
|
if (!database)
|
|
17002
17356
|
throw new Error("PostgREST snapshot must export Database from the official type generator");
|
|
17003
|
-
const program =
|
|
17357
|
+
const program = ts18.createProgram([postgrestTypes], {
|
|
17004
17358
|
strict: true,
|
|
17005
17359
|
noEmit: true,
|
|
17006
17360
|
skipLibCheck: true,
|
|
17007
17361
|
types: [],
|
|
17008
|
-
target:
|
|
17009
|
-
module:
|
|
17010
|
-
moduleResolution:
|
|
17362
|
+
target: ts18.ScriptTarget.ES2022,
|
|
17363
|
+
module: ts18.ModuleKind.ESNext,
|
|
17364
|
+
moduleResolution: ts18.ModuleResolutionKind.Bundler
|
|
17011
17365
|
});
|
|
17012
|
-
if (
|
|
17366
|
+
if (ts18.getPreEmitDiagnostics(program).length)
|
|
17013
17367
|
throw new Error("PostgREST snapshot has TypeScript errors");
|
|
17014
17368
|
const artifacts = await renderGraphql({
|
|
17015
17369
|
rootDir,
|
|
@@ -17027,11 +17381,11 @@ async function generateDatabaseContracts(options, check = false) {
|
|
|
17027
17381
|
};
|
|
17028
17382
|
await addInput(postgrestTypes);
|
|
17029
17383
|
await addInput(drizzleSchema);
|
|
17030
|
-
const drizzleProgram =
|
|
17384
|
+
const drizzleProgram = ts18.createProgram([drizzleSchema], {
|
|
17031
17385
|
noEmit: true,
|
|
17032
|
-
moduleResolution:
|
|
17033
|
-
module:
|
|
17034
|
-
target:
|
|
17386
|
+
moduleResolution: ts18.ModuleResolutionKind.Bundler,
|
|
17387
|
+
module: ts18.ModuleKind.ESNext,
|
|
17388
|
+
target: ts18.ScriptTarget.ES2022,
|
|
17035
17389
|
types: [],
|
|
17036
17390
|
skipLibCheck: true
|
|
17037
17391
|
});
|
|
@@ -17478,7 +17832,6 @@ function readProjectConfig(rootDir) {
|
|
|
17478
17832
|
skipLibCheck: true
|
|
17479
17833
|
},
|
|
17480
17834
|
errors: [],
|
|
17481
|
-
projectReferences: undefined,
|
|
17482
17835
|
configFingerprint: "defaults"
|
|
17483
17836
|
};
|
|
17484
17837
|
}
|
|
@@ -17500,7 +17853,7 @@ function readProjectConfig(rootDir) {
|
|
|
17500
17853
|
return {
|
|
17501
17854
|
options: parsed.options,
|
|
17502
17855
|
errors: parsed.errors,
|
|
17503
|
-
projectReferences: parsed.projectReferences,
|
|
17856
|
+
...parsed.projectReferences === undefined ? {} : { projectReferences: parsed.projectReferences },
|
|
17504
17857
|
configFingerprint: JSON.stringify([...configReads])
|
|
17505
17858
|
};
|
|
17506
17859
|
}
|
|
@@ -20708,7 +21061,7 @@ import { join as join4 } from "node:path";
|
|
|
20708
21061
|
// src/type-safety.ts
|
|
20709
21062
|
import { existsSync as existsSync2, readFileSync as readFileSync2 } from "node:fs";
|
|
20710
21063
|
import { dirname as dirname3, join as join3, relative as relative3, resolve as resolve3, sep as sep3 } from "node:path";
|
|
20711
|
-
import * as
|
|
21064
|
+
import * as ts10 from "@typescript/typescript6";
|
|
20712
21065
|
|
|
20713
21066
|
// src/sql-safety.ts
|
|
20714
21067
|
import * as ts8 from "@typescript/typescript6";
|
|
@@ -20751,6 +21104,198 @@ function scanDrizzleSql(sourceFile, checker, file, strict) {
|
|
|
20751
21104
|
return diagnostics;
|
|
20752
21105
|
}
|
|
20753
21106
|
|
|
21107
|
+
// src/source-semantics.ts
|
|
21108
|
+
import * as ts9 from "@typescript/typescript6";
|
|
21109
|
+
var SOURCE_SEMANTIC_DIAGNOSTIC_CODES = {
|
|
21110
|
+
"source-unsafe-any": { errorCode: "SC6009", docsUrl: "https://supacloud.dev/errors/SC6009" },
|
|
21111
|
+
"source-floating-promise": { errorCode: "SC6010", docsUrl: "https://supacloud.dev/errors/SC6010" },
|
|
21112
|
+
"source-non-exhaustive-switch": { errorCode: "SC6011", docsUrl: "https://supacloud.dev/errors/SC6011" }
|
|
21113
|
+
};
|
|
21114
|
+
function scanSourceSemantics(source, checker, file, rootDir) {
|
|
21115
|
+
const diagnostics = [];
|
|
21116
|
+
const report = (code, node, message) => {
|
|
21117
|
+
diagnostics.push({
|
|
21118
|
+
severity: "error",
|
|
21119
|
+
code,
|
|
21120
|
+
...SOURCE_SEMANTIC_DIAGNOSTIC_CODES[code],
|
|
21121
|
+
file,
|
|
21122
|
+
message,
|
|
21123
|
+
line: source.getLineAndCharacterOfPosition(node.getStart(source)).line + 1
|
|
21124
|
+
});
|
|
21125
|
+
};
|
|
21126
|
+
const unsafe = (value, target) => {
|
|
21127
|
+
if (isUnknownBoundary(target, checker) || containsAny(target, checker, new Set, rootDir))
|
|
21128
|
+
return;
|
|
21129
|
+
if (containsAny(checker.getTypeAtLocation(value), checker, new Set, rootDir)) {
|
|
21130
|
+
report("source-unsafe-any", value, "An any-containing value cannot enter a concrete type. Quarantine it as unknown and decode it before use.");
|
|
21131
|
+
}
|
|
21132
|
+
};
|
|
21133
|
+
const declared = (node) => {
|
|
21134
|
+
let hasAnyKeyword = false;
|
|
21135
|
+
const visitType = (child) => {
|
|
21136
|
+
if (child.kind === ts9.SyntaxKind.AnyKeyword)
|
|
21137
|
+
hasAnyKeyword = true;
|
|
21138
|
+
ts9.forEachChild(child, visitType);
|
|
21139
|
+
};
|
|
21140
|
+
visitType(node);
|
|
21141
|
+
if (!hasAnyKeyword && containsAny(checker.getTypeAtLocation(node), checker, new Set, rootDir)) {
|
|
21142
|
+
report("source-unsafe-any", node, "Declared application types must not hide any through aliases or generic arguments.");
|
|
21143
|
+
}
|
|
21144
|
+
};
|
|
21145
|
+
const visit = (node) => {
|
|
21146
|
+
if (ts9.isTypeAliasDeclaration(node))
|
|
21147
|
+
declared(node.type);
|
|
21148
|
+
if ((ts9.isVariableDeclaration(node) || ts9.isParameter(node) || ts9.isPropertyDeclaration(node) || ts9.isPropertySignature(node)) && node.type)
|
|
21149
|
+
declared(node.type);
|
|
21150
|
+
if (ts9.isVariableDeclaration(node) && node.initializer) {
|
|
21151
|
+
const type = checker.getTypeAtLocation(node.name);
|
|
21152
|
+
if (node.type)
|
|
21153
|
+
unsafe(node.initializer, type);
|
|
21154
|
+
else if (ts9.isIdentifier(node.name) && !ts9.isArrowFunction(node.initializer) && !ts9.isFunctionExpression(node.initializer) && !(type.flags & ts9.TypeFlags.Any) && containsAny(type, checker, new Set, rootDir)) {
|
|
21155
|
+
report("source-unsafe-any", node.name, "Inferred values must not contain any, including nested and generic result types.");
|
|
21156
|
+
}
|
|
21157
|
+
}
|
|
21158
|
+
if (ts9.isPropertyDeclaration(node) && !node.type && node.initializer && containsAny(checker.getTypeAtLocation(node.name), checker, new Set, rootDir)) {
|
|
21159
|
+
report("source-unsafe-any", node.name, "Inferred class fields must not propagate any. Decode the value or quarantine it as unknown.");
|
|
21160
|
+
}
|
|
21161
|
+
if ((ts9.isFunctionDeclaration(node) || ts9.isMethodDeclaration(node) || ts9.isArrowFunction(node) || ts9.isFunctionExpression(node)) && !node.type && node.body) {
|
|
21162
|
+
const signature = checker.getSignatureFromDeclaration(node);
|
|
21163
|
+
if (signature && containsAny(checker.getReturnTypeOfSignature(signature), checker, new Set, rootDir)) {
|
|
21164
|
+
report("source-unsafe-any", node.name ?? node, "Inferred function results must not propagate any. Return unknown at the boundary or a decoded concrete result.");
|
|
21165
|
+
}
|
|
21166
|
+
}
|
|
21167
|
+
if (ts9.isFunctionLike(node) && node.type)
|
|
21168
|
+
declared(node.type);
|
|
21169
|
+
if (ts9.isBinaryExpression(node) && node.operatorToken.kind === ts9.SyntaxKind.EqualsToken) {
|
|
21170
|
+
unsafe(node.right, checker.getTypeAtLocation(node.left));
|
|
21171
|
+
}
|
|
21172
|
+
if (ts9.isAsExpression(node) || ts9.isTypeAssertionExpression(node)) {
|
|
21173
|
+
unsafe(node.expression, checker.getTypeAtLocation(node));
|
|
21174
|
+
}
|
|
21175
|
+
if (ts9.isReturnStatement(node) && node.expression) {
|
|
21176
|
+
let owner = node.parent;
|
|
21177
|
+
while (owner && !ts9.isFunctionLike(owner))
|
|
21178
|
+
owner = owner.parent;
|
|
21179
|
+
if (owner && ts9.isFunctionLike(owner) && owner.type) {
|
|
21180
|
+
const signature = checker.getSignatureFromDeclaration(owner);
|
|
21181
|
+
if (signature)
|
|
21182
|
+
unsafe(node.expression, checker.getReturnTypeOfSignature(signature));
|
|
21183
|
+
}
|
|
21184
|
+
}
|
|
21185
|
+
if (ts9.isCallExpression(node)) {
|
|
21186
|
+
const signature = checker.getResolvedSignature(node);
|
|
21187
|
+
const parameters = signature?.getParameters() ?? [];
|
|
21188
|
+
node.arguments.forEach((argument, index) => {
|
|
21189
|
+
const parameter = parameters[index] ?? parameters.at(-1);
|
|
21190
|
+
if (!parameter)
|
|
21191
|
+
return;
|
|
21192
|
+
const type = checker.getTypeOfSymbolAtLocation(parameter, node);
|
|
21193
|
+
const declaration = parameter.valueDeclaration;
|
|
21194
|
+
const rest = declaration && ts9.isParameter(declaration) && declaration.dotDotDotToken;
|
|
21195
|
+
const target = rest ? checker.getIndexTypeOfType(type, ts9.IndexKind.Number) ?? type : type;
|
|
21196
|
+
unsafe(argument, target);
|
|
21197
|
+
});
|
|
21198
|
+
}
|
|
21199
|
+
if (ts9.isExpressionStatement(node)) {
|
|
21200
|
+
const expression = unwrap(node.expression);
|
|
21201
|
+
if (isPromise(checker.getTypeAtLocation(expression), checker, expression) && !handlesRejection(expression, checker)) {
|
|
21202
|
+
report("source-floating-promise", node, "Promise work must be awaited, returned, or have a callable rejection handler. void does not establish cancellation ownership.");
|
|
21203
|
+
}
|
|
21204
|
+
}
|
|
21205
|
+
if (ts9.isSwitchStatement(node)) {
|
|
21206
|
+
const type = checker.getTypeAtLocation(node.expression);
|
|
21207
|
+
const members = type.isUnion() ? type.types : [type];
|
|
21208
|
+
if (members.every(isFiniteLiteral)) {
|
|
21209
|
+
const cases = node.caseBlock.clauses.filter(ts9.isCaseClause);
|
|
21210
|
+
const missing = members.filter((member) => !cases.some((clause) => sameLiteral(member, checker.getTypeAtLocation(clause.expression))));
|
|
21211
|
+
if (missing.length > 0) {
|
|
21212
|
+
report("source-non-exhaustive-switch", node.expression, `Switch is missing cases for ${missing.map((member) => checker.typeToString(member)).join(", ")}. A default branch does not replace explicit union cases.`);
|
|
21213
|
+
}
|
|
21214
|
+
}
|
|
21215
|
+
}
|
|
21216
|
+
ts9.forEachChild(node, visit);
|
|
21217
|
+
};
|
|
21218
|
+
visit(source);
|
|
21219
|
+
return diagnostics;
|
|
21220
|
+
}
|
|
21221
|
+
function containsAny(type, checker, seen, rootDir) {
|
|
21222
|
+
if (type.flags & ts9.TypeFlags.Any)
|
|
21223
|
+
return true;
|
|
21224
|
+
if (seen.has(type))
|
|
21225
|
+
return false;
|
|
21226
|
+
seen.add(type);
|
|
21227
|
+
if (type.isUnionOrIntersection())
|
|
21228
|
+
return type.types.some((part) => containsAny(part, checker, seen, rootDir));
|
|
21229
|
+
const declarations = type.getSymbol()?.declarations ?? [];
|
|
21230
|
+
if (declarations.some((declaration) => ts9.isClassDeclaration(declaration) && (declaration.getSourceFile().isDeclarationFile || declaration.getSourceFile().fileName.replaceAll("\\", "/").includes("/node_modules/"))))
|
|
21231
|
+
return false;
|
|
21232
|
+
const arguments_ = isTypeReference2(type) ? checker.getTypeArguments(type) : type.aliasTypeArguments ?? [];
|
|
21233
|
+
if (arguments_.some((argument) => containsAny(argument, checker, seen, rootDir)))
|
|
21234
|
+
return true;
|
|
21235
|
+
if (checker.getSignaturesOfType(type, ts9.SignatureKind.Call).some((signature) => {
|
|
21236
|
+
const declaration = signature.getDeclaration();
|
|
21237
|
+
return declaration !== undefined && isWithinRoot(declaration.getSourceFile().fileName, rootDir) && (containsAny(checker.getReturnTypeOfSignature(signature), checker, seen, rootDir) || signature.getParameters().some((parameter) => containsAny(checker.getTypeOfSymbolAtLocation(parameter, declaration), checker, seen, rootDir)));
|
|
21238
|
+
}))
|
|
21239
|
+
return true;
|
|
21240
|
+
return checker.getPropertiesOfType(type).some((property) => {
|
|
21241
|
+
const declaration = property.valueDeclaration ?? property.declarations?.[0];
|
|
21242
|
+
return declaration !== undefined && isWithinRoot(declaration.getSourceFile().fileName, rootDir) && containsAny(checker.getTypeOfSymbolAtLocation(property, declaration), checker, seen, rootDir);
|
|
21243
|
+
});
|
|
21244
|
+
}
|
|
21245
|
+
function isWithinRoot(file, rootDir) {
|
|
21246
|
+
const normalizedFile = file.replaceAll("\\", "/");
|
|
21247
|
+
const normalizedRoot = rootDir.replaceAll("\\", "/").replace(/\/+$/, "");
|
|
21248
|
+
return normalizedFile === normalizedRoot || normalizedFile.startsWith(`${normalizedRoot}/`);
|
|
21249
|
+
}
|
|
21250
|
+
function isUnknownBoundary(type, checker) {
|
|
21251
|
+
if (type.flags & (ts9.TypeFlags.Unknown | ts9.TypeFlags.Void))
|
|
21252
|
+
return true;
|
|
21253
|
+
const promised = promiseArgument(type, checker);
|
|
21254
|
+
return promised !== undefined && Boolean(promised.flags & ts9.TypeFlags.Unknown);
|
|
21255
|
+
}
|
|
21256
|
+
function unwrap(expression) {
|
|
21257
|
+
while (ts9.isParenthesizedExpression(expression) || ts9.isVoidExpression(expression))
|
|
21258
|
+
expression = expression.expression;
|
|
21259
|
+
return expression;
|
|
21260
|
+
}
|
|
21261
|
+
function isPromise(type, checker, node) {
|
|
21262
|
+
return type.isUnion() ? type.types.some((part) => isPromise(part, checker, node)) : promiseArgument(type, checker) !== undefined;
|
|
21263
|
+
}
|
|
21264
|
+
function handlesRejection(expression, checker) {
|
|
21265
|
+
if (!ts9.isCallExpression(expression) || !ts9.isPropertyAccessExpression(expression.expression))
|
|
21266
|
+
return false;
|
|
21267
|
+
const { name, expression: receiver } = expression.expression;
|
|
21268
|
+
if (!isPromise(checker.getTypeAtLocation(receiver), checker, receiver))
|
|
21269
|
+
return false;
|
|
21270
|
+
const handler = name.text === "catch" ? expression.arguments[0] : name.text === "then" ? expression.arguments[1] : undefined;
|
|
21271
|
+
return handler !== undefined && checker.getTypeAtLocation(handler).getCallSignatures().length > 0;
|
|
21272
|
+
}
|
|
21273
|
+
function isFiniteLiteral(type) {
|
|
21274
|
+
return Boolean(type.flags & (ts9.TypeFlags.StringLiteral | ts9.TypeFlags.NumberLiteral | ts9.TypeFlags.BigIntLiteral | ts9.TypeFlags.BooleanLiteral | ts9.TypeFlags.Null | ts9.TypeFlags.Undefined));
|
|
21275
|
+
}
|
|
21276
|
+
function sameLiteral(left, right) {
|
|
21277
|
+
if (left.flags !== right.flags)
|
|
21278
|
+
return false;
|
|
21279
|
+
if (left.isStringLiteral() && right.isStringLiteral())
|
|
21280
|
+
return left.value === right.value;
|
|
21281
|
+
if (left.isNumberLiteral() && right.isNumberLiteral())
|
|
21282
|
+
return left.value === right.value;
|
|
21283
|
+
return left === right;
|
|
21284
|
+
}
|
|
21285
|
+
function isTypeReference2(type) {
|
|
21286
|
+
return Boolean(type.flags & ts9.TypeFlags.Object) && "objectFlags" in type && typeof type.objectFlags === "number" && Boolean(type.objectFlags & ts9.ObjectFlags.Reference) && "target" in type;
|
|
21287
|
+
}
|
|
21288
|
+
function promiseArgument(type, checker) {
|
|
21289
|
+
if (type.flags & (ts9.TypeFlags.Any | ts9.TypeFlags.Unknown | ts9.TypeFlags.Never))
|
|
21290
|
+
return;
|
|
21291
|
+
const then = checker.getPropertyOfType(type, "then");
|
|
21292
|
+
const declaration = then?.valueDeclaration ?? then?.declarations?.[0];
|
|
21293
|
+
if (!then || !declaration || checker.getTypeOfSymbolAtLocation(then, declaration).getCallSignatures().length === 0)
|
|
21294
|
+
return;
|
|
21295
|
+
const awaited = checker.getAwaitedType(type);
|
|
21296
|
+
return awaited !== type ? awaited : undefined;
|
|
21297
|
+
}
|
|
21298
|
+
|
|
20754
21299
|
// src/type-safety.ts
|
|
20755
21300
|
var DEFAULT_EXCLUDES = [
|
|
20756
21301
|
"**/*.test.ts",
|
|
@@ -20765,6 +21310,7 @@ var DEFAULT_EXCLUDES = [
|
|
|
20765
21310
|
];
|
|
20766
21311
|
var TYPE_SAFETY_DIAGNOSTIC_CODES = {
|
|
20767
21312
|
...SQL_SAFETY_DIAGNOSTIC_CODES,
|
|
21313
|
+
...SOURCE_SEMANTIC_DIAGNOSTIC_CODES,
|
|
20768
21314
|
"generated-any": { errorCode: "SC6001", docsUrl: "https://supacloud.dev/errors/SC6001" },
|
|
20769
21315
|
"source-any": { errorCode: "SC6002", docsUrl: "https://supacloud.dev/errors/SC6002" },
|
|
20770
21316
|
"source-type-assertion": { errorCode: "SC6003", docsUrl: "https://supacloud.dev/errors/SC6003" },
|
|
@@ -20777,7 +21323,7 @@ function scanGeneratedArtifacts(artifacts, strict = true) {
|
|
|
20777
21323
|
for (const [file, content] of Object.entries(artifacts)) {
|
|
20778
21324
|
if (content === undefined)
|
|
20779
21325
|
continue;
|
|
20780
|
-
const sourceFile =
|
|
21326
|
+
const sourceFile = ts10.createSourceFile(file, content, ts10.ScriptTarget.Latest, true, ts10.ScriptKind.TS);
|
|
20781
21327
|
for (const node of descendantsOfKind2(sourceFile, isAnyKeyword)) {
|
|
20782
21328
|
diagnostics.push(makeDiagnostic("generated-any", `生成产物 ${file} 包含 any;严格生成模式要求使用 unknown、具体接口或泛型约束。`, sourceFile, node, strict));
|
|
20783
21329
|
}
|
|
@@ -20786,36 +21332,58 @@ function scanGeneratedArtifacts(artifacts, strict = true) {
|
|
|
20786
21332
|
}
|
|
20787
21333
|
function scanProductionSource(options) {
|
|
20788
21334
|
const rootDir = resolve3(options.rootDir);
|
|
20789
|
-
const configPath =
|
|
21335
|
+
const configPath = ts10.findConfigFile(rootDir, ts10.sys.fileExists) ?? join3(rootDir, "tsconfig.json");
|
|
20790
21336
|
const projectConfig = existsSync2(configPath) ? readProjectConfig2(configPath) : {
|
|
20791
21337
|
options: {
|
|
20792
21338
|
strict: true,
|
|
21339
|
+
experimentalDecorators: true,
|
|
20793
21340
|
skipLibCheck: true,
|
|
20794
|
-
target:
|
|
20795
|
-
module:
|
|
20796
|
-
moduleResolution:
|
|
21341
|
+
target: ts10.ScriptTarget.ES2022,
|
|
21342
|
+
module: ts10.ModuleKind.ESNext,
|
|
21343
|
+
moduleResolution: ts10.ModuleResolutionKind.Bundler
|
|
20797
21344
|
},
|
|
20798
21345
|
errors: []
|
|
20799
21346
|
};
|
|
20800
21347
|
const include = options.include ?? ["**/*.ts", "**/*.tsx", "**/*.mts", "**/*.cts"];
|
|
20801
|
-
const rootNames =
|
|
20802
|
-
const compilerOptions = {
|
|
20803
|
-
|
|
21348
|
+
const rootNames = ts10.sys.readDirectory(rootDir, [".ts", ".tsx", ".mts", ".cts"], ["node_modules", "dist"], include).filter((file) => isProductionSourcePath(rootDir, file, [...DEFAULT_EXCLUDES, ...options.exclude ?? []]));
|
|
21349
|
+
const compilerOptions = {
|
|
21350
|
+
...projectConfig.options,
|
|
21351
|
+
noCheck: false,
|
|
21352
|
+
strict: true,
|
|
21353
|
+
noImplicitAny: true,
|
|
21354
|
+
strictNullChecks: true,
|
|
21355
|
+
strictFunctionTypes: true,
|
|
21356
|
+
strictBindCallApply: true,
|
|
21357
|
+
strictPropertyInitialization: true,
|
|
21358
|
+
strictBuiltinIteratorReturn: true,
|
|
21359
|
+
noImplicitThis: true,
|
|
21360
|
+
useUnknownInCatchVariables: true,
|
|
21361
|
+
alwaysStrict: true,
|
|
21362
|
+
noUncheckedIndexedAccess: true,
|
|
21363
|
+
exactOptionalPropertyTypes: true,
|
|
21364
|
+
noImplicitOverride: true,
|
|
21365
|
+
noPropertyAccessFromIndexSignature: true,
|
|
21366
|
+
noFallthroughCasesInSwitch: true,
|
|
21367
|
+
forceConsistentCasingInFileNames: true,
|
|
21368
|
+
noEmit: true
|
|
21369
|
+
};
|
|
21370
|
+
const host = ts10.createCompilerHost(compilerOptions);
|
|
20804
21371
|
host.getCurrentDirectory = () => dirname3(configPath);
|
|
20805
|
-
const program =
|
|
21372
|
+
const program = ts10.createProgram(rootNames, compilerOptions, host);
|
|
20806
21373
|
const outDir = options.outDir ? normalizeRelative(rootDir, options.outDir) : undefined;
|
|
20807
21374
|
const excludes = [...DEFAULT_EXCLUDES, ...options.exclude ?? []];
|
|
20808
21375
|
const sourceFiles = program.getSourceFiles().filter((sourceFile) => isProductionSource(rootDir, sourceFile, excludes, outDir));
|
|
20809
21376
|
const diagnostics = [...projectConfig.errors, ...program.getOptionsDiagnostics()].map((diagnostic) => ({
|
|
20810
21377
|
severity: "error",
|
|
20811
21378
|
code: "source-config",
|
|
20812
|
-
message:
|
|
21379
|
+
message: ts10.flattenDiagnosticMessageText(diagnostic.messageText, `
|
|
20813
21380
|
`),
|
|
20814
21381
|
file: diagnostic.file ? normalizeRelative(rootDir, diagnostic.file.fileName) : normalizeRelative(rootDir, configPath),
|
|
20815
21382
|
...diagnostic.file && diagnostic.start !== undefined ? { line: diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start).line + 1 } : {},
|
|
20816
21383
|
errorCode: `TS${diagnostic.code}`
|
|
20817
21384
|
}));
|
|
20818
21385
|
const checker = program.getTypeChecker();
|
|
21386
|
+
const moduleResolutionCodes = new Set([2307, 2688, 2792]);
|
|
20819
21387
|
for (const diagnostic of [
|
|
20820
21388
|
...program.getGlobalDiagnostics(),
|
|
20821
21389
|
...sourceFiles.flatMap((sourceFile) => [
|
|
@@ -20825,8 +21393,8 @@ function scanProductionSource(options) {
|
|
|
20825
21393
|
]) {
|
|
20826
21394
|
diagnostics.push({
|
|
20827
21395
|
severity: "error",
|
|
20828
|
-
code: "source-typescript",
|
|
20829
|
-
message:
|
|
21396
|
+
code: moduleResolutionCodes.has(diagnostic.code) ? "source-config" : "source-typescript",
|
|
21397
|
+
message: ts10.flattenDiagnosticMessageText(diagnostic.messageText, `
|
|
20830
21398
|
`),
|
|
20831
21399
|
...diagnostic.file ? { file: normalizeRelative(rootDir, diagnostic.file.fileName) } : {},
|
|
20832
21400
|
...diagnostic.file && diagnostic.start !== undefined ? { line: diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start).line + 1 } : {},
|
|
@@ -20835,10 +21403,11 @@ function scanProductionSource(options) {
|
|
|
20835
21403
|
}
|
|
20836
21404
|
for (const sourceFile of sourceFiles) {
|
|
20837
21405
|
scanSourceFile(sourceFile, checker, rootDir, diagnostics, options.strict ?? false);
|
|
21406
|
+
diagnostics.push(...scanSourceSemantics(sourceFile, checker, normalizeRelative(rootDir, sourceFile.fileName), rootDir));
|
|
20838
21407
|
diagnostics.push(...scanDrizzleSql(sourceFile, checker, normalizeRelative(rootDir, sourceFile.fileName), options.strict ?? false));
|
|
20839
|
-
const scanner =
|
|
20840
|
-
for (let kind = scanner.scan();kind !==
|
|
20841
|
-
if ((kind ===
|
|
21408
|
+
const scanner = ts10.createScanner(ts10.ScriptTarget.Latest, false, sourceFile.languageVariant, sourceFile.text);
|
|
21409
|
+
for (let kind = scanner.scan();kind !== ts10.SyntaxKind.EndOfFileToken; kind = scanner.scan()) {
|
|
21410
|
+
if ((kind === ts10.SyntaxKind.SingleLineCommentTrivia || kind === ts10.SyntaxKind.MultiLineCommentTrivia) && /@ts-(?:ignore|nocheck|expect-error)\b/.test(scanner.getTokenText())) {
|
|
20842
21411
|
diagnostics.push({
|
|
20843
21412
|
severity: "error",
|
|
20844
21413
|
code: "source-type-suppression",
|
|
@@ -20858,22 +21427,22 @@ function scanSourceFile(sourceFile, checker, rootDir, diagnostics, strict) {
|
|
|
20858
21427
|
diagnostics.push(makeDiagnostic("source-any", "生产源码使用了显式 any;请改用 unknown、具体接口或泛型约束。", sourceFile, node, strict, rootDir));
|
|
20859
21428
|
}
|
|
20860
21429
|
for (const node of descendants(sourceFile)) {
|
|
20861
|
-
if (
|
|
20862
|
-
if (
|
|
21430
|
+
if (ts10.isAsExpression(node)) {
|
|
21431
|
+
if (ts10.isAsExpression(node.parent) || ts10.isTypeAssertionExpression(node.parent))
|
|
20863
21432
|
continue;
|
|
20864
21433
|
const assertedType = node.type.getText(sourceFile);
|
|
20865
21434
|
if (assertedType === "const")
|
|
20866
21435
|
continue;
|
|
20867
21436
|
diagnostics.push(makeDiagnostic("source-type-assertion", `生产源码包含类型断言 ${node.getText(sourceFile)};请优先使用类型守卫、satisfies 或显式边界解析。`, sourceFile, node, strict, rootDir));
|
|
20868
|
-
} else if (
|
|
20869
|
-
if (
|
|
21437
|
+
} else if (ts10.isTypeAssertionExpression(node)) {
|
|
21438
|
+
if (ts10.isAsExpression(node.parent) || ts10.isTypeAssertionExpression(node.parent))
|
|
20870
21439
|
continue;
|
|
20871
21440
|
diagnostics.push(makeDiagnostic("source-type-assertion", `生产源码包含类型断言 ${node.getText(sourceFile)};请优先使用类型守卫、satisfies 或显式边界解析。`, sourceFile, node, strict, rootDir));
|
|
20872
|
-
} else if (
|
|
21441
|
+
} else if (ts10.isNonNullExpression(node)) {
|
|
20873
21442
|
diagnostics.push(makeDiagnostic("source-non-null-assertion", `生产源码包含非空断言 ${node.getText(sourceFile)};请显式处理 null/undefined。`, sourceFile, node, strict, rootDir));
|
|
20874
21443
|
}
|
|
20875
21444
|
}
|
|
20876
|
-
for (const declaration of descendantsOfKind2(sourceFile,
|
|
21445
|
+
for (const declaration of descendantsOfKind2(sourceFile, ts10.isVariableDeclaration)) {
|
|
20877
21446
|
const initializer = declaration.initializer;
|
|
20878
21447
|
if (!initializer || declaration.type)
|
|
20879
21448
|
continue;
|
|
@@ -20889,11 +21458,11 @@ function scanSourceFile(sourceFile, checker, rootDir, diagnostics, strict) {
|
|
|
20889
21458
|
if (isLetDeclaration(declaration) && isLiteralSyntax(initializer) && !isLiteralType(declarationType)) {
|
|
20890
21459
|
diagnostics.push(makeDiagnostic("source-implicit-widening", `变量 ${declaration.name.getText(sourceFile)} 的字面量类型从 ${checker.typeToString(initializerType, initializer)} 隐式宽化为 ${checker.typeToString(declarationType, declaration)};请补充类型或使用 const。`, sourceFile, declaration, strict, rootDir));
|
|
20891
21460
|
}
|
|
20892
|
-
if (
|
|
21461
|
+
if (ts10.isObjectLiteralExpression(initializer) && isConstDeclaration(declaration) && initializer.getText(sourceFile).length > 0 && initializer.properties.some((property) => ts10.isPropertyAssignment(property) && property.initializer !== undefined && !ts10.isAsExpression(property.initializer) && isLiteralExpression(property.initializer))) {
|
|
20893
21462
|
diagnostics.push(makeDiagnostic("source-implicit-widening", `常量对象 ${declaration.name.getText(sourceFile)} 的字面量属性会隐式宽化;请补充对象类型或使用 as const。`, sourceFile, declaration, strict, rootDir));
|
|
20894
21463
|
}
|
|
20895
21464
|
}
|
|
20896
|
-
for (const parameter of descendantsOfKind2(sourceFile,
|
|
21465
|
+
for (const parameter of descendantsOfKind2(sourceFile, ts10.isParameter)) {
|
|
20897
21466
|
if (parameter.type)
|
|
20898
21467
|
continue;
|
|
20899
21468
|
for (const name of bindingNames(parameter.name)) {
|
|
@@ -20904,10 +21473,10 @@ function scanSourceFile(sourceFile, checker, rootDir, diagnostics, strict) {
|
|
|
20904
21473
|
}
|
|
20905
21474
|
}
|
|
20906
21475
|
function readProjectConfig2(configPath) {
|
|
20907
|
-
const config =
|
|
21476
|
+
const config = ts10.readConfigFile(configPath, (file) => readFileSync2(file, "utf8"));
|
|
20908
21477
|
if (config.error)
|
|
20909
21478
|
return { options: {}, errors: [config.error] };
|
|
20910
|
-
const parsed =
|
|
21479
|
+
const parsed = ts10.parseJsonConfigFileContent(config.config, ts10.sys, dirname3(configPath));
|
|
20911
21480
|
return { options: parsed.options, errors: parsed.errors };
|
|
20912
21481
|
}
|
|
20913
21482
|
function isProductionSource(rootDir, sourceFile, excludes, outDir) {
|
|
@@ -20927,42 +21496,42 @@ function globMatches(value, pattern) {
|
|
|
20927
21496
|
return new RegExp(`^${escaped}$`).test(value);
|
|
20928
21497
|
}
|
|
20929
21498
|
function bindingNames(name) {
|
|
20930
|
-
if (
|
|
21499
|
+
if (ts10.isIdentifier(name))
|
|
20931
21500
|
return [name];
|
|
20932
|
-
return name.elements.flatMap((element) =>
|
|
21501
|
+
return name.elements.flatMap((element) => ts10.isBindingElement(element) ? bindingNames(element.name) : []);
|
|
20933
21502
|
}
|
|
20934
21503
|
function isLiteralExpression(node) {
|
|
20935
21504
|
if (!node)
|
|
20936
21505
|
return false;
|
|
20937
21506
|
return [
|
|
20938
|
-
|
|
20939
|
-
|
|
20940
|
-
|
|
20941
|
-
|
|
21507
|
+
ts10.SyntaxKind.StringLiteral,
|
|
21508
|
+
ts10.SyntaxKind.NumericLiteral,
|
|
21509
|
+
ts10.SyntaxKind.TrueKeyword,
|
|
21510
|
+
ts10.SyntaxKind.FalseKeyword
|
|
20942
21511
|
].includes(node.kind);
|
|
20943
21512
|
}
|
|
20944
21513
|
function isLiteralSyntax(node) {
|
|
20945
|
-
return
|
|
21514
|
+
return ts10.isStringLiteral(node) || ts10.isNumericLiteral(node) || node.kind === ts10.SyntaxKind.TrueKeyword || node.kind === ts10.SyntaxKind.FalseKeyword;
|
|
20946
21515
|
}
|
|
20947
21516
|
function isLiteralType(type) {
|
|
20948
|
-
return (type.flags & (
|
|
21517
|
+
return (type.flags & (ts10.TypeFlags.StringLiteral | ts10.TypeFlags.NumberLiteral | ts10.TypeFlags.BooleanLiteral | ts10.TypeFlags.BigIntLiteral)) !== 0;
|
|
20949
21518
|
}
|
|
20950
21519
|
function isAnyType(type) {
|
|
20951
|
-
return (type.flags &
|
|
21520
|
+
return (type.flags & ts10.TypeFlags.Any) !== 0;
|
|
20952
21521
|
}
|
|
20953
21522
|
function isLetDeclaration(declaration) {
|
|
20954
|
-
return
|
|
21523
|
+
return ts10.isVariableDeclarationList(declaration.parent) && (declaration.parent.flags & ts10.NodeFlags.Let) !== 0;
|
|
20955
21524
|
}
|
|
20956
21525
|
function isConstDeclaration(declaration) {
|
|
20957
|
-
return
|
|
21526
|
+
return ts10.isVariableDeclarationList(declaration.parent) && (declaration.parent.flags & ts10.NodeFlags.Const) !== 0;
|
|
20958
21527
|
}
|
|
20959
21528
|
function descendants(root) {
|
|
20960
21529
|
const result = [];
|
|
20961
21530
|
const visit = (node) => {
|
|
20962
21531
|
result.push(node);
|
|
20963
|
-
|
|
21532
|
+
ts10.forEachChild(node, visit);
|
|
20964
21533
|
};
|
|
20965
|
-
|
|
21534
|
+
ts10.forEachChild(root, visit);
|
|
20966
21535
|
return result;
|
|
20967
21536
|
}
|
|
20968
21537
|
function descendantsOfKind2(root, predicate) {
|
|
@@ -20970,9 +21539,9 @@ function descendantsOfKind2(root, predicate) {
|
|
|
20970
21539
|
const visit = (node) => {
|
|
20971
21540
|
if (predicate(node))
|
|
20972
21541
|
result.push(node);
|
|
20973
|
-
|
|
21542
|
+
ts10.forEachChild(node, visit);
|
|
20974
21543
|
};
|
|
20975
|
-
|
|
21544
|
+
ts10.forEachChild(root, visit);
|
|
20976
21545
|
return result;
|
|
20977
21546
|
}
|
|
20978
21547
|
function makeDiagnostic(code, message, fileOrSourceFile, node, strict, rootDir) {
|
|
@@ -20980,7 +21549,7 @@ function makeDiagnostic(code, message, fileOrSourceFile, node, strict, rootDir)
|
|
|
20980
21549
|
const file = typeof fileOrSourceFile === "string" ? fileOrSourceFile : rootDir ? normalizeRelative(rootDir, fileOrSourceFile.fileName) : fileOrSourceFile.fileName;
|
|
20981
21550
|
const meta = TYPE_SAFETY_DIAGNOSTIC_CODES[code];
|
|
20982
21551
|
return {
|
|
20983
|
-
severity: strict ? "error" : "warn",
|
|
21552
|
+
severity: strict || code === "source-any" || code === "generated-any" ? "error" : "warn",
|
|
20984
21553
|
code,
|
|
20985
21554
|
message,
|
|
20986
21555
|
file,
|
|
@@ -20993,7 +21562,7 @@ function normalizeRelative(rootDir, filePath) {
|
|
|
20993
21562
|
return relative3(rootDir, filePath).split(sep3).join("/").replace(/^\.\//, "");
|
|
20994
21563
|
}
|
|
20995
21564
|
function isAnyKeyword(node) {
|
|
20996
|
-
return node.kind ===
|
|
21565
|
+
return node.kind === ts10.SyntaxKind.AnyKeyword;
|
|
20997
21566
|
}
|
|
20998
21567
|
|
|
20999
21568
|
// src/compile.ts
|
|
@@ -21154,11 +21723,12 @@ async function compileProject(options) {
|
|
|
21154
21723
|
}, options.strict ?? false));
|
|
21155
21724
|
}
|
|
21156
21725
|
const hasErrors = diagnostics.some((diagnostic) => diagnostic.severity === "error");
|
|
21726
|
+
const hasTypeErrors = diagnostics.some(({ severity, code }) => severity === "error" && (code.startsWith("source-") || code === "generated-any"));
|
|
21157
21727
|
const generatedOptions = {
|
|
21158
21728
|
...options,
|
|
21159
21729
|
...options.cache ? { artifactHashes: options.cache.generatedHashes } : {}
|
|
21160
21730
|
};
|
|
21161
|
-
const written = !hasErrors || options.writeOnError === true ? await writeRenderedApplication(rendered, generatedOptions) : [];
|
|
21731
|
+
const written = !hasErrors || options.writeOnError === true && !hasTypeErrors ? await writeRenderedApplication(rendered, generatedOptions) : [];
|
|
21162
21732
|
if (!hasErrors) {
|
|
21163
21733
|
for (const [filename, content] of Object.entries(graphql.files)) {
|
|
21164
21734
|
const path = join4(options.outDir, filename);
|
|
@@ -21255,8 +21825,8 @@ async function checkProject(options) {
|
|
|
21255
21825
|
}
|
|
21256
21826
|
function resolveTypeSafety(options) {
|
|
21257
21827
|
return {
|
|
21258
|
-
noAnyInGenerated:
|
|
21259
|
-
scanProductionSource:
|
|
21828
|
+
noAnyInGenerated: true,
|
|
21829
|
+
scanProductionSource: true,
|
|
21260
21830
|
...options.typeSafety?.exclude ? { exclude: options.typeSafety.exclude } : {}
|
|
21261
21831
|
};
|
|
21262
21832
|
}
|
|
@@ -21541,19 +22111,7 @@ function createIncrementalCompiler() {
|
|
|
21541
22111
|
const snapshot = !options.graphql && changedPaths && previousSnapshot && previousSnapshot.optionsKey === optionsKey ? await updateSnapshot(previousSnapshot, options, changedPaths) : await createSnapshot(options);
|
|
21542
22112
|
const changedFiles = changedPaths && previousSnapshot ? diffFiles(previousSnapshot.files, snapshot.files) : diffFiles(previousSnapshot?.files, snapshot.files);
|
|
21543
22113
|
const activeCache = options.cache ?? cache;
|
|
21544
|
-
const cacheHit = Boolean(previousSnapshot && previousSnapshot.optionsKey === snapshot.optionsKey && previousCache === activeCache && changedFiles.length === 0)
|
|
21545
|
-
if (cacheHit && previousResult) {
|
|
21546
|
-
return {
|
|
21547
|
-
...previousResult,
|
|
21548
|
-
stats: {
|
|
21549
|
-
cacheHit: true,
|
|
21550
|
-
changedFiles: [],
|
|
21551
|
-
affectedModules: [],
|
|
21552
|
-
reusedModules: previousResult.graph.modules.map((m) => m.name),
|
|
21553
|
-
reanalyzedModules: []
|
|
21554
|
-
}
|
|
21555
|
-
};
|
|
21556
|
-
}
|
|
22114
|
+
const cacheHit = Boolean(previousSnapshot && previousSnapshot.optionsKey === snapshot.optionsKey && previousCache === activeCache && changedFiles.length === 0);
|
|
21557
22115
|
if (!activeCache.dependencyGraph && previousResult) {
|
|
21558
22116
|
activeCache.dependencyGraph = new ModuleDependencyGraph(previousResult.graph.modules);
|
|
21559
22117
|
}
|
|
@@ -21569,7 +22127,7 @@ function createIncrementalCompiler() {
|
|
|
21569
22127
|
activeCache.dependencyGraph = new ModuleDependencyGraph(result.graph.modules);
|
|
21570
22128
|
}
|
|
21571
22129
|
const stats = {
|
|
21572
|
-
cacheHit:
|
|
22130
|
+
cacheHit: cacheHit && !result.diagnostics.some(({ severity }) => severity === "error"),
|
|
21573
22131
|
changedFiles,
|
|
21574
22132
|
affectedModules,
|
|
21575
22133
|
reusedModules,
|
|
@@ -22123,10 +22681,10 @@ function resolveSupacloudConfig(config = {}, cwd = process.cwd()) {
|
|
|
22123
22681
|
...resolved.detectOrphanModules === undefined ? {} : { detectOrphanModules: resolved.detectOrphanModules },
|
|
22124
22682
|
effect: resolved.effect === undefined ? { ...DEFAULT_SUPACLOUD_CONFIG.effect } : { ...DEFAULT_SUPACLOUD_CONFIG.effect, ...resolved.effect },
|
|
22125
22683
|
treeShakeUnusedProviders: resolved.treeShakeUnusedProviders ?? DEFAULT_SUPACLOUD_CONFIG.treeShakeUnusedProviders,
|
|
22126
|
-
graphql
|
|
22684
|
+
...resolved.graphql === undefined || resolved.graphql === false ? {} : { graphql: {
|
|
22127
22685
|
...resolved.graphql,
|
|
22128
22686
|
schema: resolve12(cwd, resolved.graphql.schema)
|
|
22129
|
-
}
|
|
22687
|
+
} }
|
|
22130
22688
|
};
|
|
22131
22689
|
}
|
|
22132
22690
|
async function loadSupacloudConfig(cwd = process.cwd()) {
|
|
@@ -22454,7 +23012,7 @@ function formatDeliveryPlan(result) {
|
|
|
22454
23012
|
import { mkdir as mkdir3, mkdtemp, readFile as readFile7, realpath as realpath4, rename as rename4, rm as rm2 } from "node:fs/promises";
|
|
22455
23013
|
import { readFileSync as readFileSync3 } from "node:fs";
|
|
22456
23014
|
import { dirname as dirname9, join as join10, relative as relative10, resolve as resolve16, sep as sep10 } from "node:path";
|
|
22457
|
-
import * as
|
|
23015
|
+
import * as ts16 from "@typescript/typescript6";
|
|
22458
23016
|
|
|
22459
23017
|
// src/delivery-build-schema.ts
|
|
22460
23018
|
init_delivery_build_schema();
|
|
@@ -22496,22 +23054,22 @@ init_delivery_files2();
|
|
|
22496
23054
|
import { isBuiltin } from "node:module";
|
|
22497
23055
|
import { readFile as readFile6 } from "node:fs/promises";
|
|
22498
23056
|
import { join as join9, resolve as resolve14 } from "node:path";
|
|
22499
|
-
import * as
|
|
23057
|
+
import * as ts15 from "@typescript/typescript6";
|
|
22500
23058
|
|
|
22501
23059
|
// src/delivery-imports.ts
|
|
22502
|
-
import * as
|
|
23060
|
+
import * as ts14 from "@typescript/typescript6";
|
|
22503
23061
|
function staticDeliveryImports(path, contents) {
|
|
22504
23062
|
if (!/\.[cm]?[jt]sx?$/.test(path))
|
|
22505
23063
|
return contents;
|
|
22506
|
-
const source =
|
|
23064
|
+
const source = ts14.createSourceFile(path, new TextDecoder().decode(contents), ts14.ScriptTarget.Latest, true);
|
|
22507
23065
|
const computed = [];
|
|
22508
23066
|
function scan(node) {
|
|
22509
|
-
if (
|
|
23067
|
+
if (ts14.isCallExpression(node) && (node.expression.kind === ts14.SyntaxKind.ImportKeyword || ts14.isIdentifier(node.expression) && node.expression.text === "require")) {
|
|
22510
23068
|
const argument = node.arguments[0];
|
|
22511
|
-
if (!argument || !
|
|
23069
|
+
if (!argument || !ts14.isStringLiteral(argument) && !ts14.isNoSubstitutionTemplateLiteral(argument))
|
|
22512
23070
|
computed.push(node);
|
|
22513
23071
|
}
|
|
22514
|
-
|
|
23072
|
+
ts14.forEachChild(node, scan);
|
|
22515
23073
|
}
|
|
22516
23074
|
scan(source);
|
|
22517
23075
|
if (computed.length === 0)
|
|
@@ -22519,36 +23077,36 @@ function staticDeliveryImports(path, contents) {
|
|
|
22519
23077
|
const reject = () => {
|
|
22520
23078
|
throw new Error("Computed module loading is not supported in independent delivery bundles.");
|
|
22521
23079
|
};
|
|
22522
|
-
if (!
|
|
23080
|
+
if (!ts14.isExternalModule(source))
|
|
22523
23081
|
return reject();
|
|
22524
|
-
const host =
|
|
23082
|
+
const host = ts14.createCompilerHost({ noLib: true, noResolve: true, allowJs: true });
|
|
22525
23083
|
host.getSourceFile = (name) => name === path ? source : undefined;
|
|
22526
|
-
const checker =
|
|
23084
|
+
const checker = ts14.createProgram([path], { noLib: true, noResolve: true, allowJs: true }, host).getTypeChecker();
|
|
22527
23085
|
const replacements = new Map;
|
|
22528
23086
|
const removed = new Set;
|
|
22529
23087
|
for (const call of computed) {
|
|
22530
23088
|
let visit = function(node) {
|
|
22531
|
-
const referenced =
|
|
22532
|
-
if (
|
|
23089
|
+
const referenced = ts14.isIdentifier(node) ? ts14.isShorthandPropertyAssignment(node.parent) ? checker.getShorthandAssignmentValueSymbol(node.parent) : ts14.isExportSpecifier(node.parent) ? checker.getExportSpecifierLocalTargetSymbol(node.parent) : checker.getSymbolAtLocation(node) : undefined;
|
|
23090
|
+
if (ts14.isIdentifier(node) && node !== declarationName && referenced === symbol) {
|
|
22533
23091
|
const use = node.parent;
|
|
22534
|
-
if (!
|
|
23092
|
+
if (!ts14.isCallExpression(use) || use.expression !== node || use.arguments.length !== 1 || use.questionDotToken || use.typeArguments?.length)
|
|
22535
23093
|
return reject();
|
|
22536
23094
|
const value = use.arguments[0];
|
|
22537
|
-
if (!value || !
|
|
23095
|
+
if (!value || !ts14.isStringLiteral(value) && !ts14.isNoSubstitutionTemplateLiteral(value))
|
|
22538
23096
|
return reject();
|
|
22539
23097
|
references++;
|
|
22540
|
-
replacements.set(use,
|
|
23098
|
+
replacements.set(use, ts14.factory.createCallExpression(call.expression, undefined, [value]));
|
|
22541
23099
|
}
|
|
22542
|
-
|
|
23100
|
+
ts14.forEachChild(node, visit);
|
|
22543
23101
|
};
|
|
22544
23102
|
const statement = call.parent;
|
|
22545
23103
|
const block = statement.parent;
|
|
22546
23104
|
const declaration = block.parent;
|
|
22547
|
-
if (call.expression.kind !==
|
|
23105
|
+
if (call.expression.kind !== ts14.SyntaxKind.ImportKeyword || call.arguments.length !== 1 || !ts14.isReturnStatement(statement) || !ts14.isBlock(block) || block.statements.length !== 1 || !ts14.isFunctionDeclaration(declaration) || declaration.parent !== source || !declaration.name || declaration.modifiers?.length || declaration.asteriskToken || declaration.typeParameters?.length || declaration.parameters.length !== 1)
|
|
22548
23106
|
return reject();
|
|
22549
23107
|
const parameter = declaration.parameters[0];
|
|
22550
23108
|
const argument = call.arguments[0];
|
|
22551
|
-
if (!parameter || !
|
|
23109
|
+
if (!parameter || !ts14.isIdentifier(parameter.name) || parameter.initializer || parameter.dotDotDotToken || !argument || !ts14.isIdentifier(argument) || checker.getSymbolAtLocation(argument) !== checker.getSymbolAtLocation(parameter.name))
|
|
22552
23110
|
return reject();
|
|
22553
23111
|
const symbol = checker.getSymbolAtLocation(declaration.name);
|
|
22554
23112
|
if (!symbol || symbol.declarations?.length !== 1)
|
|
@@ -22560,22 +23118,22 @@ function staticDeliveryImports(path, contents) {
|
|
|
22560
23118
|
return reject();
|
|
22561
23119
|
removed.add(declaration);
|
|
22562
23120
|
}
|
|
22563
|
-
const transformed =
|
|
23121
|
+
const transformed = ts14.transform(source, [(context) => {
|
|
22564
23122
|
const visit = (node) => {
|
|
22565
|
-
if (
|
|
23123
|
+
if (ts14.isFunctionDeclaration(node) && removed.has(node))
|
|
22566
23124
|
return;
|
|
22567
|
-
const replacement =
|
|
23125
|
+
const replacement = ts14.isCallExpression(node) ? replacements.get(node) : undefined;
|
|
22568
23126
|
if (replacement)
|
|
22569
23127
|
return replacement;
|
|
22570
|
-
return
|
|
23128
|
+
return ts14.visitEachChild(node, visit, context);
|
|
22571
23129
|
};
|
|
22572
|
-
return (node) =>
|
|
23130
|
+
return (node) => ts14.visitNode(node, visit, ts14.isSourceFile) ?? node;
|
|
22573
23131
|
}]);
|
|
22574
23132
|
try {
|
|
22575
23133
|
const transformedSource = transformed.transformed[0];
|
|
22576
23134
|
if (!transformedSource)
|
|
22577
23135
|
return reject();
|
|
22578
|
-
return new TextEncoder().encode(
|
|
23136
|
+
return new TextEncoder().encode(ts14.createPrinter().printFile(transformedSource));
|
|
22579
23137
|
} finally {
|
|
22580
23138
|
transformed.dispose();
|
|
22581
23139
|
}
|
|
@@ -22723,16 +23281,16 @@ async function bundleDeliveryTargetInProcess(name, code, project, generatedDirec
|
|
|
22723
23281
|
const bytes = new Uint8Array(await output.arrayBuffer());
|
|
22724
23282
|
if (/\.[cm]?js$/.test(path)) {
|
|
22725
23283
|
let check = function(node) {
|
|
22726
|
-
const specifier =
|
|
22727
|
-
if (specifier &&
|
|
23284
|
+
const specifier = ts15.isImportDeclaration(node) || ts15.isExportDeclaration(node) ? node.moduleSpecifier : ts15.isCallExpression(node) && (node.expression.kind === ts15.SyntaxKind.ImportKeyword || ts15.isIdentifier(node.expression) && /^(?:__)?require$/.test(node.expression.text) || ts15.isPropertyAccessExpression(node.expression) && node.expression.name.text === "require" && ts15.isMetaProperty(node.expression.expression) && node.expression.expression.keywordToken === ts15.SyntaxKind.ImportKeyword) ? node.arguments[0] : undefined;
|
|
23285
|
+
if (specifier && ts15.isStringLiteralLike(specifier)) {
|
|
22728
23286
|
if (!isBuiltin(specifier.text) && specifier.text !== "bun" && !specifier.text.startsWith("bun:")) {
|
|
22729
23287
|
throw new Error("Independent bundles cannot retain external package imports.");
|
|
22730
23288
|
}
|
|
22731
23289
|
runtimeImports.add(specifier.text);
|
|
22732
23290
|
}
|
|
22733
|
-
|
|
23291
|
+
ts15.forEachChild(node, check);
|
|
22734
23292
|
};
|
|
22735
|
-
const source =
|
|
23293
|
+
const source = ts15.createSourceFile(path, new TextDecoder().decode(bytes), ts15.ScriptTarget.Latest, true);
|
|
22736
23294
|
check(source);
|
|
22737
23295
|
}
|
|
22738
23296
|
files.set(`bundle/${path}`, bytes);
|
|
@@ -22751,16 +23309,16 @@ function renderDeliveryRuntimeIdentity() {
|
|
|
22751
23309
|
return `
|
|
22752
23310
|
function deliveryRuntimeIdentity(kind: "http" | "worker") {
|
|
22753
23311
|
const env = deliveryProcess.env;
|
|
22754
|
-
if (env
|
|
23312
|
+
if (env["SUPACLOUD_ACTIVATION_ID"] === undefined) return null;
|
|
22755
23313
|
const identity = {
|
|
22756
23314
|
schema: "supacloud.application-runtime.v1",
|
|
22757
|
-
project_ref: env
|
|
22758
|
-
application_id: env
|
|
22759
|
-
environment_id: env
|
|
22760
|
-
release_id: env
|
|
22761
|
-
activation_id: env
|
|
22762
|
-
target: env
|
|
22763
|
-
object_id: env
|
|
23315
|
+
project_ref: env["SUPACLOUD_PROJECT_REF"],
|
|
23316
|
+
application_id: env["SUPACLOUD_APPLICATION_ID"],
|
|
23317
|
+
environment_id: env["SUPACLOUD_ENVIRONMENT_ID"],
|
|
23318
|
+
release_id: env["SUPACLOUD_RELEASE_ID"],
|
|
23319
|
+
activation_id: env["SUPACLOUD_ACTIVATION_ID"],
|
|
23320
|
+
target: env["SUPACLOUD_TARGET"],
|
|
23321
|
+
object_id: env["SUPACLOUD_OBJECT_ID"],
|
|
22764
23322
|
kind, pid: deliveryProcess.pid,
|
|
22765
23323
|
};
|
|
22766
23324
|
const matches = (value: string | undefined, pattern: RegExp) => typeof value === "string" && pattern.test(value);
|
|
@@ -22793,8 +23351,8 @@ interface DeliveryHttpHost {
|
|
|
22793
23351
|
|
|
22794
23352
|
async function startDeliveryHttp(signal: AbortSignal, shutdownTimeout: number, startDeadline: () => void) {
|
|
22795
23353
|
const identity = deliveryRuntimeIdentity("http");
|
|
22796
|
-
const port = Number(deliveryProcess.env
|
|
22797
|
-
const hostname = deliveryProcess.env
|
|
23354
|
+
const port = Number(deliveryProcess.env["PORT"] ?? "3000");
|
|
23355
|
+
const hostname = deliveryProcess.env["HOST"] ?? "127.0.0.1";
|
|
22798
23356
|
if (!Number.isInteger(port) || port < 0 || port > 65535 || hostname.length === 0) {
|
|
22799
23357
|
throw new Error("Invalid delivery HTTP listener configuration.");
|
|
22800
23358
|
}
|
|
@@ -22862,7 +23420,7 @@ async function startDeliveryHttp(signal: AbortSignal, shutdownTimeout: number, s
|
|
|
22862
23420
|
|
|
22863
23421
|
{
|
|
22864
23422
|
const lifecycle = new AbortController();
|
|
22865
|
-
const shutdownTimeout = Number(deliveryProcess.env
|
|
23423
|
+
const shutdownTimeout = Number(deliveryProcess.env["SHUTDOWN_TIMEOUT_MS"] ?? "10000");
|
|
22866
23424
|
let running: Awaited<ReturnType<typeof startDeliveryHttp>>;
|
|
22867
23425
|
let deadline: ReturnType<typeof setTimeout> | undefined;
|
|
22868
23426
|
const finish = (failed: boolean) => {
|
|
@@ -22930,7 +23488,7 @@ interface DeliveryWorkerHost {
|
|
|
22930
23488
|
|
|
22931
23489
|
{
|
|
22932
23490
|
const lifecycle = new AbortController();
|
|
22933
|
-
const shutdownTimeout = Number(deliveryProcess.env
|
|
23491
|
+
const shutdownTimeout = Number(deliveryProcess.env["SHUTDOWN_TIMEOUT_MS"] ?? "10000");
|
|
22934
23492
|
let host: DeliveryWorkerHost | undefined;
|
|
22935
23493
|
let running = false;
|
|
22936
23494
|
let runtimeFailed = false;
|
|
@@ -22998,7 +23556,7 @@ interface DeliveryWorkerHost {
|
|
|
22998
23556
|
const candidate = await createHost(createCompiledModules(), { signal: lifecycle.signal });
|
|
22999
23557
|
if (!candidate || typeof candidate.close !== "function") throw new Error("Invalid delivery worker host.");
|
|
23000
23558
|
host = candidate;
|
|
23001
|
-
const execution = deliveryProcess.env
|
|
23559
|
+
const execution = deliveryProcess.env["SUPACLOUD_WORKER_EXECUTION"];
|
|
23002
23560
|
if (execution) {
|
|
23003
23561
|
const expected: unknown = JSON.parse(Buffer.from(execution, "base64").toString("utf8"));
|
|
23004
23562
|
if (!deliveryPolicyEqual(host.execution, expected) || typeof host.health !== "function" || !host.failure) {
|
|
@@ -23102,7 +23660,7 @@ async function buildDeliveryProject(options, delivery) {
|
|
|
23102
23660
|
const settings = parseDeliveryOptions(delivery);
|
|
23103
23661
|
if (typeof Bun === "undefined")
|
|
23104
23662
|
throw new Error("Independent delivery builds require Bun.");
|
|
23105
|
-
const configPath =
|
|
23663
|
+
const configPath = ts16.findConfigFile(resolve16(options.rootDir), ts16.sys.fileExists);
|
|
23106
23664
|
if (!configPath)
|
|
23107
23665
|
throw new Error("Independent delivery builds require a project tsconfig.json.");
|
|
23108
23666
|
const lexicalProject = dirname9(configPath);
|
|
@@ -23118,8 +23676,8 @@ async function buildDeliveryProject(options, delivery) {
|
|
|
23118
23676
|
if (inside(generatedRoot, sourceRoot))
|
|
23119
23677
|
throw new Error("Output must not contain the application source root.");
|
|
23120
23678
|
const configInputs = new Map;
|
|
23121
|
-
const parsedConfig =
|
|
23122
|
-
...
|
|
23679
|
+
const parsedConfig = ts16.getParsedCommandLineOfConfigFile(await realpath4(configPath), {}, {
|
|
23680
|
+
...ts16.sys,
|
|
23123
23681
|
readFile(path) {
|
|
23124
23682
|
const contents = readFileSync3(path, "utf8");
|
|
23125
23683
|
configInputs.set(resolve16(path), digest(contents));
|
|
@@ -23239,7 +23797,7 @@ async function buildDeliveryProject(options, delivery) {
|
|
|
23239
23797
|
for (const [name, contents] of Object.entries(generated))
|
|
23240
23798
|
await writeArtifact(stage, `generated/${name}`, contents);
|
|
23241
23799
|
{
|
|
23242
|
-
const program =
|
|
23800
|
+
const program = ts16.createProgram({
|
|
23243
23801
|
rootNames: [
|
|
23244
23802
|
...parsedConfig.fileNames.filter((path) => !inside(generatedRoot, path)),
|
|
23245
23803
|
...Object.keys(generated).map((name) => join10(stage, "generated", name))
|
|
@@ -23247,12 +23805,12 @@ async function buildDeliveryProject(options, delivery) {
|
|
|
23247
23805
|
options: { ...parsedConfig.options, rootDir: project },
|
|
23248
23806
|
...parsedConfig.projectReferences ? { projectReferences: parsedConfig.projectReferences } : {}
|
|
23249
23807
|
});
|
|
23250
|
-
const diagnostics =
|
|
23251
|
-
if (diagnostics.some((item) => item.category ===
|
|
23252
|
-
return failed(diagnostics.filter((item) => item.category ===
|
|
23808
|
+
const diagnostics = ts16.getPreEmitDiagnostics(program);
|
|
23809
|
+
if (diagnostics.some((item) => item.category === ts16.DiagnosticCategory.Error)) {
|
|
23810
|
+
return failed(diagnostics.filter((item) => item.category === ts16.DiagnosticCategory.Error).map((item) => ({
|
|
23253
23811
|
severity: "error",
|
|
23254
23812
|
code: "delivery-generated-type-error",
|
|
23255
|
-
message:
|
|
23813
|
+
message: ts16.flattenDiagnosticMessageText(item.messageText, `
|
|
23256
23814
|
`),
|
|
23257
23815
|
...item.file ? { file: item.file.fileName } : {}
|
|
23258
23816
|
})));
|
|
@@ -23398,7 +23956,7 @@ async function buildDeliveryProject(options, delivery) {
|
|
|
23398
23956
|
// src/migrations.ts
|
|
23399
23957
|
import { rename as rename5, readFile as readFile9, writeFile as writeFile4, rm as rm3 } from "node:fs/promises";
|
|
23400
23958
|
import { relative as relative11, resolve as resolve18 } from "node:path";
|
|
23401
|
-
import * as
|
|
23959
|
+
import * as ts17 from "@typescript/typescript6";
|
|
23402
23960
|
|
|
23403
23961
|
// src/migration-policy.ts
|
|
23404
23962
|
import { readFile as readFile8 } from "node:fs/promises";
|
|
@@ -23406,10 +23964,10 @@ import { readFileSync as readFileSync4 } from "node:fs";
|
|
|
23406
23964
|
import { resolve as resolve17 } from "node:path";
|
|
23407
23965
|
|
|
23408
23966
|
// src/migration-app-version.ts
|
|
23409
|
-
var MIGRATION_APP_VERSION = "0.
|
|
23967
|
+
var MIGRATION_APP_VERSION = "0.25.0";
|
|
23410
23968
|
|
|
23411
23969
|
// src/migration-elysia-version.ts
|
|
23412
|
-
var MIGRATION_ELYSIA_VERSION = "0.29.
|
|
23970
|
+
var MIGRATION_ELYSIA_VERSION = "0.29.1";
|
|
23413
23971
|
|
|
23414
23972
|
// src/migration-policy.ts
|
|
23415
23973
|
var cachedCompilerVersion;
|
|
@@ -23450,29 +24008,29 @@ async function checkMigrationDependencies(rootDir) {
|
|
|
23450
24008
|
// src/migrations.ts
|
|
23451
24009
|
var ROUTE_DECORATORS2 = new Set(["Get", "Post", "Put", "Patch", "Delete", "Head", "Options"]);
|
|
23452
24010
|
var MIGRATION_COMPILER_OPTIONS = {
|
|
23453
|
-
target:
|
|
23454
|
-
module:
|
|
23455
|
-
moduleResolution:
|
|
24011
|
+
target: ts17.ScriptTarget.ES2022,
|
|
24012
|
+
module: ts17.ModuleKind.ESNext,
|
|
24013
|
+
moduleResolution: ts17.ModuleResolutionKind.Bundler,
|
|
23456
24014
|
noEmit: true,
|
|
23457
24015
|
skipLibCheck: true
|
|
23458
24016
|
};
|
|
23459
24017
|
function migrationCompilerOptions(rootDir) {
|
|
23460
24018
|
if (!rootDir)
|
|
23461
24019
|
return MIGRATION_COMPILER_OPTIONS;
|
|
23462
|
-
const configPath =
|
|
24020
|
+
const configPath = ts17.findConfigFile(rootDir, ts17.sys.fileExists);
|
|
23463
24021
|
if (!configPath)
|
|
23464
24022
|
return MIGRATION_COMPILER_OPTIONS;
|
|
23465
24023
|
const configHost = {
|
|
23466
|
-
...
|
|
24024
|
+
...ts17.sys,
|
|
23467
24025
|
onUnRecoverableConfigFileDiagnostic: (_diagnostic) => {}
|
|
23468
24026
|
};
|
|
23469
|
-
const parsed =
|
|
24027
|
+
const parsed = ts17.getParsedCommandLineOfConfigFile(configPath, {}, configHost);
|
|
23470
24028
|
if (!parsed || parsed.errors.length > 0)
|
|
23471
24029
|
return MIGRATION_COMPILER_OPTIONS;
|
|
23472
24030
|
return { ...parsed.options, noEmit: true, skipLibCheck: true };
|
|
23473
24031
|
}
|
|
23474
24032
|
function propertyName2(property) {
|
|
23475
|
-
if (
|
|
24033
|
+
if (ts17.isIdentifier(property) || ts17.isStringLiteral(property) || ts17.isNumericLiteral(property))
|
|
23476
24034
|
return property.text;
|
|
23477
24035
|
return;
|
|
23478
24036
|
}
|
|
@@ -23482,7 +24040,7 @@ function lineOf2(sourceFile, node) {
|
|
|
23482
24040
|
function resolveSymbol(symbol, checker) {
|
|
23483
24041
|
if (!symbol)
|
|
23484
24042
|
return;
|
|
23485
|
-
for (let guard = 0;guard < 4 && (symbol.flags &
|
|
24043
|
+
for (let guard = 0;guard < 4 && (symbol.flags & ts17.SymbolFlags.Alias) !== 0; guard += 1) {
|
|
23486
24044
|
const aliased = checker.getAliasedSymbol(symbol);
|
|
23487
24045
|
if (aliased === symbol)
|
|
23488
24046
|
break;
|
|
@@ -23491,12 +24049,12 @@ function resolveSymbol(symbol, checker) {
|
|
|
23491
24049
|
return symbol;
|
|
23492
24050
|
}
|
|
23493
24051
|
function symbolForExpression(expression, checker) {
|
|
23494
|
-
const location =
|
|
24052
|
+
const location = ts17.isIdentifier(expression) ? expression : ts17.isPropertyAccessExpression(expression) ? expression.name : ts17.isElementAccessExpression(expression) && expression.argumentExpression && ts17.isStringLiteral(expression.argumentExpression) ? expression : undefined;
|
|
23495
24053
|
return location ? resolveSymbol(checker.getSymbolAtLocation(location), checker) : undefined;
|
|
23496
24054
|
}
|
|
23497
24055
|
function unwrapExpression(expression) {
|
|
23498
24056
|
let current = expression;
|
|
23499
|
-
while (
|
|
24057
|
+
while (ts17.isAsExpression(current) || ts17.isSatisfiesExpression(current) || ts17.isParenthesizedExpression(current) || ts17.isTypeAssertionExpression(current)) {
|
|
23500
24058
|
current = current.expression;
|
|
23501
24059
|
}
|
|
23502
24060
|
return current;
|
|
@@ -23511,7 +24069,7 @@ function isRouteDecoratorCall(node, checker) {
|
|
|
23511
24069
|
if (node.arguments.length < 2)
|
|
23512
24070
|
return false;
|
|
23513
24071
|
const name = node.expression.getText(node.getSourceFile());
|
|
23514
|
-
if (
|
|
24072
|
+
if (ts17.isIdentifier(node.expression) && ROUTE_DECORATORS2.has(node.expression.text))
|
|
23515
24073
|
return true;
|
|
23516
24074
|
if (ROUTE_DECORATORS2.has(name))
|
|
23517
24075
|
return true;
|
|
@@ -23525,14 +24083,14 @@ function resolveStaticObjectLiteral2(input, checker, seen = new Set) {
|
|
|
23525
24083
|
if (seen.has(expression))
|
|
23526
24084
|
return;
|
|
23527
24085
|
seen.add(expression);
|
|
23528
|
-
if (
|
|
24086
|
+
if (ts17.isObjectLiteralExpression(expression))
|
|
23529
24087
|
return expression;
|
|
23530
|
-
if (
|
|
24088
|
+
if (ts17.isCallExpression(expression) && isDefineRouteContractCall(expression, checker)) {
|
|
23531
24089
|
return resolveStaticObjectLiteral2(expression.arguments[0], checker, seen);
|
|
23532
24090
|
}
|
|
23533
24091
|
const symbol = symbolForExpression(expression, checker);
|
|
23534
24092
|
for (const declaration of symbol?.declarations ?? []) {
|
|
23535
|
-
if (
|
|
24093
|
+
if (ts17.isVariableDeclaration(declaration) && declaration.initializer) {
|
|
23536
24094
|
const resolved = resolveStaticObjectLiteral2(declaration.initializer, checker, seen);
|
|
23537
24095
|
if (resolved)
|
|
23538
24096
|
return resolved;
|
|
@@ -23546,7 +24104,7 @@ function displayFile(rootDir, fileName) {
|
|
|
23546
24104
|
}
|
|
23547
24105
|
function createMigrationProgram(fileNames, sourceOverrides, rootDir) {
|
|
23548
24106
|
const compilerOptions = migrationCompilerOptions(rootDir);
|
|
23549
|
-
const host =
|
|
24107
|
+
const host = ts17.createCompilerHost(compilerOptions);
|
|
23550
24108
|
const getSourceFile = host.getSourceFile.bind(host);
|
|
23551
24109
|
const fileExists = host.fileExists.bind(host);
|
|
23552
24110
|
const readFile = host.readFile.bind(host);
|
|
@@ -23555,16 +24113,16 @@ function createMigrationProgram(fileNames, sourceOverrides, rootDir) {
|
|
|
23555
24113
|
host.readFile = (fileName) => sourceOverrides.get(resolve18(fileName)) ?? readFile(fileName);
|
|
23556
24114
|
host.getSourceFile = (fileName, languageVersion, onError, shouldCreateNewSourceFile) => {
|
|
23557
24115
|
const source = sourceOverrides.get(resolve18(fileName));
|
|
23558
|
-
return source === undefined ? getSourceFile(fileName, languageVersion, onError, shouldCreateNewSourceFile) :
|
|
24116
|
+
return source === undefined ? getSourceFile(fileName, languageVersion, onError, shouldCreateNewSourceFile) : ts17.createSourceFile(fileName, source, languageVersion, true);
|
|
23559
24117
|
};
|
|
23560
24118
|
host.getCurrentDirectory = () => rootDir ?? currentDirectory();
|
|
23561
|
-
return
|
|
24119
|
+
return ts17.createProgram(fileNames, compilerOptions, host);
|
|
23562
24120
|
}
|
|
23563
24121
|
function routeResponseProperties(object) {
|
|
23564
|
-
const responseProperties = object.properties.filter((property) =>
|
|
24122
|
+
const responseProperties = object.properties.filter((property) => ts17.isPropertyAssignment(property) && propertyName2(property.name) === "response");
|
|
23565
24123
|
return {
|
|
23566
24124
|
response: responseProperties[0],
|
|
23567
|
-
hasResponses: object.properties.some((property) => (
|
|
24125
|
+
hasResponses: object.properties.some((property) => (ts17.isPropertyAssignment(property) || ts17.isShorthandPropertyAssignment(property)) && propertyName2(property.name) === "responses"),
|
|
23568
24126
|
duplicateResponse: responseProperties.length > 1
|
|
23569
24127
|
};
|
|
23570
24128
|
}
|
|
@@ -23584,7 +24142,7 @@ function planRouteResponseMigration(sourceFiles, checker, rootDir, includedFiles
|
|
|
23584
24142
|
if (!includedFiles.has(sourcePath))
|
|
23585
24143
|
continue;
|
|
23586
24144
|
const visit = (node) => {
|
|
23587
|
-
if (
|
|
24145
|
+
if (ts17.isCallExpression(node) && isRouteDecoratorCall(node, checker)) {
|
|
23588
24146
|
const options = node.arguments[1];
|
|
23589
24147
|
const object = options && resolveStaticObjectLiteral2(options, checker);
|
|
23590
24148
|
if (object) {
|
|
@@ -23604,7 +24162,7 @@ function planRouteResponseMigration(sourceFiles, checker, rootDir, includedFiles
|
|
|
23604
24162
|
}
|
|
23605
24163
|
}
|
|
23606
24164
|
}
|
|
23607
|
-
|
|
24165
|
+
ts17.forEachChild(node, visit);
|
|
23608
24166
|
};
|
|
23609
24167
|
visit(sourceFile);
|
|
23610
24168
|
}
|
|
@@ -23771,7 +24329,7 @@ async function migrateProject(options) {
|
|
|
23771
24329
|
}
|
|
23772
24330
|
}
|
|
23773
24331
|
const include = options.include ?? ["**/*.ts", "**/*.tsx", "**/*.mts", "**/*.cts"];
|
|
23774
|
-
const files =
|
|
24332
|
+
const files = ts17.sys.readDirectory(rootDir, [".ts", ".tsx", ".mts", ".cts"], ["node_modules", "dist", "generated"], include).sort();
|
|
23775
24333
|
const results = [];
|
|
23776
24334
|
const issues = [];
|
|
23777
24335
|
const pendingWrites = new Map;
|
|
@@ -23915,30 +24473,30 @@ function resolveSchema(value, document, seen = new Set) {
|
|
|
23915
24473
|
const schema = recordValue(value);
|
|
23916
24474
|
if (!schema)
|
|
23917
24475
|
return;
|
|
23918
|
-
const ref = stringValue(schema
|
|
24476
|
+
const ref = stringValue(schema["$ref"]);
|
|
23919
24477
|
if (!ref || !ref.startsWith("#/components/schemas/"))
|
|
23920
24478
|
return schema;
|
|
23921
24479
|
if (seen.has(ref))
|
|
23922
24480
|
return schema;
|
|
23923
24481
|
const name = decodeJsonPointerPart(ref.slice("#/components/schemas/".length));
|
|
23924
|
-
const components = recordValue(document
|
|
23925
|
-
const schemas = recordValue(components?.schemas);
|
|
24482
|
+
const components = recordValue(document["components"]);
|
|
24483
|
+
const schemas = recordValue(components?.["schemas"]);
|
|
23926
24484
|
const target = schemas?.[name];
|
|
23927
24485
|
if (target === undefined)
|
|
23928
24486
|
return schema;
|
|
23929
24487
|
return resolveSchema(target, document, new Set([...seen, ref]));
|
|
23930
24488
|
}
|
|
23931
24489
|
function schemaEnum(value) {
|
|
23932
|
-
return Array.isArray(value?.enum) ? value
|
|
24490
|
+
return Array.isArray(value?.["enum"]) ? value["enum"] : undefined;
|
|
23933
24491
|
}
|
|
23934
24492
|
function schemaProperties(value) {
|
|
23935
|
-
return recordValue(value?.properties);
|
|
24493
|
+
return recordValue(value?.["properties"]);
|
|
23936
24494
|
}
|
|
23937
24495
|
function schemaRequired(value) {
|
|
23938
|
-
return new Set(arrayValue(value?.required).filter((item) => typeof item === "string"));
|
|
24496
|
+
return new Set(arrayValue(value?.["required"]).filter((item) => typeof item === "string"));
|
|
23939
24497
|
}
|
|
23940
24498
|
function schemaType(value) {
|
|
23941
|
-
return value?.type;
|
|
24499
|
+
return value?.["type"];
|
|
23942
24500
|
}
|
|
23943
24501
|
function addChange(changes, change) {
|
|
23944
24502
|
if (changes.some((item) => item.kind === change.kind && item.code === change.code && item.path === change.path && item.message === change.message))
|
|
@@ -23982,7 +24540,7 @@ function compareSchema(baseValue, currentValue, baseDocument, currentDocument, p
|
|
|
23982
24540
|
if (baseProperties && currentProperties) {
|
|
23983
24541
|
for (const name of sortedKeys2(baseProperties)) {
|
|
23984
24542
|
if (currentProperties[name] === undefined) {
|
|
23985
|
-
const inputRemovalIsBreaking = baseSchema
|
|
24543
|
+
const inputRemovalIsBreaking = baseSchema["additionalProperties"] === false;
|
|
23986
24544
|
if (direction === "output" || inputRemovalIsBreaking) {
|
|
23987
24545
|
addChange(changes, {
|
|
23988
24546
|
kind: "breaking",
|
|
@@ -24009,7 +24567,7 @@ function compareSchema(baseValue, currentValue, baseDocument, currentDocument, p
|
|
|
24009
24567
|
});
|
|
24010
24568
|
}
|
|
24011
24569
|
}
|
|
24012
|
-
if (baseSchema
|
|
24570
|
+
if (baseSchema["additionalProperties"] !== false && currentSchema["additionalProperties"] === false) {
|
|
24013
24571
|
addChange(changes, {
|
|
24014
24572
|
kind: "breaking",
|
|
24015
24573
|
code: "request-additional-properties-rejected",
|
|
@@ -24032,13 +24590,13 @@ function compareSchema(baseValue, currentValue, baseDocument, currentDocument, p
|
|
|
24032
24590
|
}
|
|
24033
24591
|
function parameterKey(value) {
|
|
24034
24592
|
const parameter = recordValue(value);
|
|
24035
|
-
const name = stringValue(parameter?.name);
|
|
24036
|
-
const location = stringValue(parameter?.in);
|
|
24593
|
+
const name = stringValue(parameter?.["name"]);
|
|
24594
|
+
const location = stringValue(parameter?.["in"]);
|
|
24037
24595
|
return name && location ? `${location}:${name}` : undefined;
|
|
24038
24596
|
}
|
|
24039
24597
|
function operationParameters(pathItem, operation) {
|
|
24040
24598
|
const result = new Map;
|
|
24041
|
-
for (const source of [pathItem
|
|
24599
|
+
for (const source of [pathItem["parameters"], operation["parameters"]]) {
|
|
24042
24600
|
for (const item of arrayValue(source)) {
|
|
24043
24601
|
const parameter = recordValue(item);
|
|
24044
24602
|
const key = parameterKey(parameter);
|
|
@@ -24049,7 +24607,7 @@ function operationParameters(pathItem, operation) {
|
|
|
24049
24607
|
return result;
|
|
24050
24608
|
}
|
|
24051
24609
|
function parameterSchema(value) {
|
|
24052
|
-
return value
|
|
24610
|
+
return value["schema"];
|
|
24053
24611
|
}
|
|
24054
24612
|
function compareParameters(basePathItem, currentPathItem, baseOperation, currentOperation, baseDocument, currentDocument, path, changes) {
|
|
24055
24613
|
const baseParameters = operationParameters(basePathItem, baseOperation);
|
|
@@ -24066,7 +24624,7 @@ function compareParameters(basePathItem, currentPathItem, baseOperation, current
|
|
|
24066
24624
|
});
|
|
24067
24625
|
continue;
|
|
24068
24626
|
}
|
|
24069
|
-
if (currentParameter
|
|
24627
|
+
if (currentParameter["required"] === true && baseParameter["required"] !== true) {
|
|
24070
24628
|
addChange(changes, {
|
|
24071
24629
|
kind: "breaking",
|
|
24072
24630
|
code: "parameter-required",
|
|
@@ -24085,16 +24643,16 @@ function compareParameters(basePathItem, currentPathItem, baseOperation, current
|
|
|
24085
24643
|
if (!parameter)
|
|
24086
24644
|
continue;
|
|
24087
24645
|
addChange(changes, {
|
|
24088
|
-
kind: parameter
|
|
24089
|
-
code: parameter
|
|
24646
|
+
kind: parameter["required"] === true ? "breaking" : "non-breaking",
|
|
24647
|
+
code: parameter["required"] === true ? "parameter-required" : "parameter-added",
|
|
24090
24648
|
path: `${path}.parameters.${key}`,
|
|
24091
|
-
message: parameter
|
|
24649
|
+
message: parameter["required"] === true ? "A new required parameter was added." : "An optional parameter was added."
|
|
24092
24650
|
});
|
|
24093
24651
|
}
|
|
24094
24652
|
}
|
|
24095
24653
|
function compareRequestBody(baseOperation, currentOperation, baseDocument, currentDocument, path, changes) {
|
|
24096
|
-
const baseBody = recordValue(baseOperation
|
|
24097
|
-
const currentBody = recordValue(currentOperation
|
|
24654
|
+
const baseBody = recordValue(baseOperation["requestBody"]);
|
|
24655
|
+
const currentBody = recordValue(currentOperation["requestBody"]);
|
|
24098
24656
|
if (!baseBody || !currentBody) {
|
|
24099
24657
|
if (baseBody && !currentBody) {
|
|
24100
24658
|
addChange(changes, {
|
|
@@ -24103,7 +24661,7 @@ function compareRequestBody(baseOperation, currentOperation, baseDocument, curre
|
|
|
24103
24661
|
path: `${path}.requestBody`,
|
|
24104
24662
|
message: "A request body from the previous contract was removed."
|
|
24105
24663
|
});
|
|
24106
|
-
} else if (!baseBody && currentBody?.required === true) {
|
|
24664
|
+
} else if (!baseBody && currentBody?.["required"] === true) {
|
|
24107
24665
|
addChange(changes, {
|
|
24108
24666
|
kind: "breaking",
|
|
24109
24667
|
code: "request-body-required",
|
|
@@ -24120,7 +24678,7 @@ function compareRequestBody(baseOperation, currentOperation, baseDocument, curre
|
|
|
24120
24678
|
}
|
|
24121
24679
|
return;
|
|
24122
24680
|
}
|
|
24123
|
-
if (currentBody
|
|
24681
|
+
if (currentBody["required"] === true && baseBody["required"] !== true) {
|
|
24124
24682
|
addChange(changes, {
|
|
24125
24683
|
kind: "breaking",
|
|
24126
24684
|
code: "request-body-required",
|
|
@@ -24128,8 +24686,8 @@ function compareRequestBody(baseOperation, currentOperation, baseDocument, curre
|
|
|
24128
24686
|
message: "An optional request body became required."
|
|
24129
24687
|
});
|
|
24130
24688
|
}
|
|
24131
|
-
const baseContent = recordValue(baseBody
|
|
24132
|
-
const currentContent = recordValue(currentBody
|
|
24689
|
+
const baseContent = recordValue(baseBody["content"]);
|
|
24690
|
+
const currentContent = recordValue(currentBody["content"]);
|
|
24133
24691
|
for (const mediaType of sortedKeys2(baseContent)) {
|
|
24134
24692
|
const baseMedia = recordValue(baseContent?.[mediaType]);
|
|
24135
24693
|
const currentMedia = recordValue(currentContent?.[mediaType]);
|
|
@@ -24142,14 +24700,14 @@ function compareRequestBody(baseOperation, currentOperation, baseDocument, curre
|
|
|
24142
24700
|
});
|
|
24143
24701
|
continue;
|
|
24144
24702
|
}
|
|
24145
|
-
if (baseMedia
|
|
24146
|
-
compareSchema(baseMedia
|
|
24703
|
+
if (baseMedia["schema"] !== undefined && currentMedia["schema"] !== undefined) {
|
|
24704
|
+
compareSchema(baseMedia["schema"], currentMedia["schema"], baseDocument, currentDocument, `${path}.requestBody.content.${mediaType}.schema`, "input", changes);
|
|
24147
24705
|
}
|
|
24148
24706
|
}
|
|
24149
24707
|
}
|
|
24150
24708
|
function compareResponses(baseOperation, currentOperation, baseDocument, currentDocument, path, changes) {
|
|
24151
|
-
const baseResponses = recordValue(baseOperation
|
|
24152
|
-
const currentResponses = recordValue(currentOperation
|
|
24709
|
+
const baseResponses = recordValue(baseOperation["responses"]);
|
|
24710
|
+
const currentResponses = recordValue(currentOperation["responses"]);
|
|
24153
24711
|
for (const status of sortedKeys2(baseResponses)) {
|
|
24154
24712
|
const baseResponse = recordValue(baseResponses?.[status]);
|
|
24155
24713
|
const currentResponse = recordValue(currentResponses?.[status]);
|
|
@@ -24162,8 +24720,8 @@ function compareResponses(baseOperation, currentOperation, baseDocument, current
|
|
|
24162
24720
|
});
|
|
24163
24721
|
continue;
|
|
24164
24722
|
}
|
|
24165
|
-
const baseContent = recordValue(baseResponse
|
|
24166
|
-
const currentContent = recordValue(currentResponse
|
|
24723
|
+
const baseContent = recordValue(baseResponse["content"]);
|
|
24724
|
+
const currentContent = recordValue(currentResponse["content"]);
|
|
24167
24725
|
for (const mediaType of sortedKeys2(baseContent)) {
|
|
24168
24726
|
const baseMedia = recordValue(baseContent?.[mediaType]);
|
|
24169
24727
|
const currentMedia = recordValue(currentContent?.[mediaType]);
|
|
@@ -24176,8 +24734,8 @@ function compareResponses(baseOperation, currentOperation, baseDocument, current
|
|
|
24176
24734
|
});
|
|
24177
24735
|
continue;
|
|
24178
24736
|
}
|
|
24179
|
-
if (baseMedia
|
|
24180
|
-
compareSchema(baseMedia
|
|
24737
|
+
if (baseMedia["schema"] !== undefined && currentMedia["schema"] !== undefined) {
|
|
24738
|
+
compareSchema(baseMedia["schema"], currentMedia["schema"], baseDocument, currentDocument, `${path}.responses.${status}.content.${mediaType}.schema`, "output", changes);
|
|
24181
24739
|
}
|
|
24182
24740
|
}
|
|
24183
24741
|
}
|
|
@@ -24196,8 +24754,8 @@ function compareOperation(basePathItem, currentPathItem, baseOperation, currentO
|
|
|
24196
24754
|
compareParameters(basePathItem, currentPathItem, baseOperation, currentOperation, baseDocument, currentDocument, path, changes);
|
|
24197
24755
|
compareRequestBody(baseOperation, currentOperation, baseDocument, currentDocument, path, changes);
|
|
24198
24756
|
compareResponses(baseOperation, currentOperation, baseDocument, currentDocument, path, changes);
|
|
24199
|
-
const baseSecurity = baseOperation
|
|
24200
|
-
const currentSecurity = currentOperation
|
|
24757
|
+
const baseSecurity = baseOperation["security"];
|
|
24758
|
+
const currentSecurity = currentOperation["security"];
|
|
24201
24759
|
if (Array.isArray(currentSecurity) && currentSecurity.length > 0 && (!Array.isArray(baseSecurity) || baseSecurity.length === 0)) {
|
|
24202
24760
|
addChange(changes, {
|
|
24203
24761
|
kind: "breaking",
|
|
@@ -24208,8 +24766,8 @@ function compareOperation(basePathItem, currentPathItem, baseOperation, currentO
|
|
|
24208
24766
|
}
|
|
24209
24767
|
}
|
|
24210
24768
|
function compareComponents(baseDocument, currentDocument, changes) {
|
|
24211
|
-
const baseComponents = recordValue(baseDocument
|
|
24212
|
-
const currentComponents = recordValue(currentDocument
|
|
24769
|
+
const baseComponents = recordValue(baseDocument["components"]);
|
|
24770
|
+
const currentComponents = recordValue(currentDocument["components"]);
|
|
24213
24771
|
for (const group of COMPONENT_GROUPS) {
|
|
24214
24772
|
const baseGroup = recordValue(baseComponents?.[group]);
|
|
24215
24773
|
const currentGroup = recordValue(currentComponents?.[group]);
|
|
@@ -24236,10 +24794,10 @@ function compareComponents(baseDocument, currentDocument, changes) {
|
|
|
24236
24794
|
}
|
|
24237
24795
|
}
|
|
24238
24796
|
function parseOpenApiDocument(value) {
|
|
24239
|
-
if (!isRecord(value) || typeof value
|
|
24797
|
+
if (!isRecord(value) || typeof value["openapi"] !== "string" || !/^3\.[0-9]+(?:\.[0-9]+)?$/.test(value["openapi"]) || !isRecord(value["info"]) || !isRecord(value["paths"])) {
|
|
24240
24798
|
throw new OpenApiDocumentError;
|
|
24241
24799
|
}
|
|
24242
|
-
return { ...value, openapi: value
|
|
24800
|
+
return { ...value, openapi: value["openapi"], info: value["info"], paths: value["paths"] };
|
|
24243
24801
|
}
|
|
24244
24802
|
function serializeOpenApiJson(document, space = 2) {
|
|
24245
24803
|
const parsed = parseOpenApiDocument(document);
|
|
@@ -24288,7 +24846,7 @@ async function loadGeneratedOpenApiDocument(modulePath) {
|
|
|
24288
24846
|
const loaded = await import(moduleUrl.href);
|
|
24289
24847
|
if (!isRecord(loaded))
|
|
24290
24848
|
throw new OpenApiDocumentError;
|
|
24291
|
-
return parseOpenApiDocument(loaded
|
|
24849
|
+
return parseOpenApiDocument(loaded["OPENAPI_DOCUMENT"]);
|
|
24292
24850
|
} catch (error) {
|
|
24293
24851
|
if (error instanceof OpenApiDocumentError)
|
|
24294
24852
|
throw error;
|
|
@@ -24379,7 +24937,7 @@ function isRecord2(value) {
|
|
|
24379
24937
|
function arrayLength(value) {
|
|
24380
24938
|
return Array.isArray(value) ? value.length : undefined;
|
|
24381
24939
|
}
|
|
24382
|
-
async function
|
|
24940
|
+
async function sha2563(path) {
|
|
24383
24941
|
return createHash11("sha256").update(await readFile11(path)).digest("hex");
|
|
24384
24942
|
}
|
|
24385
24943
|
function overallStatus(findings) {
|
|
@@ -24448,16 +25006,19 @@ async function assessMigration(options) {
|
|
|
24448
25006
|
};
|
|
24449
25007
|
try {
|
|
24450
25008
|
const parsed = JSON.parse(await readFile11(contractsManifestPath, "utf8"));
|
|
24451
|
-
if (!isRecord2(parsed) || parsed
|
|
25009
|
+
if (!isRecord2(parsed) || parsed["version"] !== 1)
|
|
24452
25010
|
throw new Error("invalid manifest");
|
|
25011
|
+
const commands = arrayLength(parsed["commands"]);
|
|
25012
|
+
const routes = arrayLength(parsed["routes"]);
|
|
25013
|
+
const permissions = arrayLength(parsed["permissions"]);
|
|
24453
25014
|
contractsManifest = {
|
|
24454
25015
|
path: contractsManifestPath,
|
|
24455
25016
|
present: true,
|
|
24456
|
-
sha256: await
|
|
25017
|
+
sha256: await sha2563(contractsManifestPath),
|
|
24457
25018
|
version: 1,
|
|
24458
|
-
...
|
|
24459
|
-
...
|
|
24460
|
-
...
|
|
25019
|
+
...commands === undefined ? {} : { commands },
|
|
25020
|
+
...routes === undefined ? {} : { routes },
|
|
25021
|
+
...permissions === undefined ? {} : { permissions }
|
|
24461
25022
|
};
|
|
24462
25023
|
} catch {
|
|
24463
25024
|
findings.push({
|
|
@@ -24476,9 +25037,9 @@ async function assessMigration(options) {
|
|
|
24476
25037
|
const diff = diffOpenApiDocuments(await readOpenApiJson(baselinePath), await readOpenApiJson(currentPath));
|
|
24477
25038
|
openApi = {
|
|
24478
25039
|
baselinePath,
|
|
24479
|
-
baselineSha256: await
|
|
25040
|
+
baselineSha256: await sha2563(baselinePath),
|
|
24480
25041
|
currentPath,
|
|
24481
|
-
currentSha256: await
|
|
25042
|
+
currentSha256: await sha2563(currentPath),
|
|
24482
25043
|
diff
|
|
24483
25044
|
};
|
|
24484
25045
|
if (!diff.ok) {
|
|
@@ -24688,15 +25249,20 @@ function checkGraphqlCompatibility(schema, documents, policy = {}) {
|
|
|
24688
25249
|
try {
|
|
24689
25250
|
parsed = parse6(document.source);
|
|
24690
25251
|
} catch (error) {
|
|
24691
|
-
diagnostics.push({
|
|
25252
|
+
diagnostics.push({
|
|
25253
|
+
severity: "error",
|
|
25254
|
+
code: "graphql-document-invalid",
|
|
25255
|
+
message: error instanceof Error ? error.message : String(error),
|
|
25256
|
+
...document.path === undefined ? {} : { file: document.path }
|
|
25257
|
+
});
|
|
24692
25258
|
continue;
|
|
24693
25259
|
}
|
|
24694
25260
|
diagnostics.push(...validate2(schema, parsed).map((error) => ({
|
|
24695
25261
|
severity: "error",
|
|
24696
25262
|
code: "graphql-validation",
|
|
24697
25263
|
message: error.message,
|
|
24698
|
-
file: document.path,
|
|
24699
|
-
line: error.locations
|
|
25264
|
+
...document.path === undefined ? {} : { file: document.path },
|
|
25265
|
+
...error.locations?.[0]?.line === undefined ? {} : { line: error.locations[0].line }
|
|
24700
25266
|
})));
|
|
24701
25267
|
const fragmentDefinitions = new Map(parsed.definitions.filter((definition) => definition.kind === Kind2.FRAGMENT_DEFINITION).map((definition) => [definition.name.value, definition]));
|
|
24702
25268
|
for (const definition of parsed.definitions) {
|
|
@@ -24704,7 +25270,10 @@ function checkGraphqlCompatibility(schema, documents, policy = {}) {
|
|
|
24704
25270
|
continue;
|
|
24705
25271
|
const result = operationReport(schema, definition, fragmentDefinitions, policy);
|
|
24706
25272
|
operations.push(result.report);
|
|
24707
|
-
diagnostics.push(...result.diagnostics.map((item) => ({
|
|
25273
|
+
diagnostics.push(...result.diagnostics.map((item) => ({
|
|
25274
|
+
...item,
|
|
25275
|
+
...document.path === undefined ? {} : { file: document.path }
|
|
25276
|
+
})));
|
|
24708
25277
|
}
|
|
24709
25278
|
}
|
|
24710
25279
|
return { ok: diagnostics.every((item) => item.severity !== "error"), features: graphqlFeatureMatrix(schema), operations, diagnostics };
|