@forgeax/engine-pack 0.0.0-dev.8d955ade1c79
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/LICENSE +202 -0
- package/README.md +429 -0
- package/dist/.tsbuildinfo +1 -0
- package/dist/__tests__/ai-recovery.unit.test.d.ts +2 -0
- package/dist/__tests__/ai-recovery.unit.test.d.ts.map +1 -0
- package/dist/__tests__/artifact-path.test.d.ts +2 -0
- package/dist/__tests__/artifact-path.test.d.ts.map +1 -0
- package/dist/__tests__/asset-evidence-error-hints.test.d.ts +2 -0
- package/dist/__tests__/asset-evidence-error-hints.test.d.ts.map +1 -0
- package/dist/__tests__/asset-evidence-lifecycle.test.d.ts +2 -0
- package/dist/__tests__/asset-evidence-lifecycle.test.d.ts.map +1 -0
- package/dist/__tests__/asset-evidence-schema.test.d.ts +2 -0
- package/dist/__tests__/asset-evidence-schema.test.d.ts.map +1 -0
- package/dist/__tests__/atlas-cli-region-mismatch.test.d.ts +2 -0
- package/dist/__tests__/atlas-cli-region-mismatch.test.d.ts.map +1 -0
- package/dist/__tests__/atlas-error-code-owner.test-d.d.ts +2 -0
- package/dist/__tests__/atlas-error-code-owner.test-d.d.ts.map +1 -0
- package/dist/__tests__/cli-asset-evidence.integration.test.d.ts +2 -0
- package/dist/__tests__/cli-asset-evidence.integration.test.d.ts.map +1 -0
- package/dist/__tests__/cli.unit.test.d.ts +2 -0
- package/dist/__tests__/cli.unit.test.d.ts.map +1 -0
- package/dist/__tests__/evidence-source-inventory.unit.test.d.ts +2 -0
- package/dist/__tests__/evidence-source-inventory.unit.test.d.ts.map +1 -0
- package/dist/__tests__/guid-collision.unit.test.d.ts +2 -0
- package/dist/__tests__/guid-collision.unit.test.d.ts.map +1 -0
- package/dist/__tests__/guid-validator-surface.unit.test.d.ts +2 -0
- package/dist/__tests__/guid-validator-surface.unit.test.d.ts.map +1 -0
- package/dist/__tests__/load-asset-config.test.d.ts +2 -0
- package/dist/__tests__/load-asset-config.test.d.ts.map +1 -0
- package/dist/__tests__/material-cook-dependencies.unit.test.d.ts +2 -0
- package/dist/__tests__/material-cook-dependencies.unit.test.d.ts.map +1 -0
- package/dist/__tests__/material-cook-receipt.unit.test.d.ts +2 -0
- package/dist/__tests__/material-cook-receipt.unit.test.d.ts.map +1 -0
- package/dist/__tests__/material-cook-schema.unit.test.d.ts +2 -0
- package/dist/__tests__/material-cook-schema.unit.test.d.ts.map +1 -0
- package/dist/__tests__/mesh-bin-consumer-surface.unit.test.d.ts +2 -0
- package/dist/__tests__/mesh-bin-consumer-surface.unit.test.d.ts.map +1 -0
- package/dist/__tests__/mesh-bin-contract.unit.test.d.ts +2 -0
- package/dist/__tests__/mesh-bin-contract.unit.test.d.ts.map +1 -0
- package/dist/__tests__/meta-schema-optional.test.d.ts +2 -0
- package/dist/__tests__/meta-schema-optional.test.d.ts.map +1 -0
- package/dist/__tests__/meta-source-overrides.unit.test.d.ts +2 -0
- package/dist/__tests__/meta-source-overrides.unit.test.d.ts.map +1 -0
- package/dist/__tests__/native-cooker-registry.test.d.ts +2 -0
- package/dist/__tests__/native-cooker-registry.test.d.ts.map +1 -0
- package/dist/__tests__/offline-evidence-artifact-verification-owner.test-d.d.ts +2 -0
- package/dist/__tests__/offline-evidence-artifact-verification-owner.test-d.d.ts.map +1 -0
- package/dist/__tests__/offline-evidence.integration.test.d.ts +2 -0
- package/dist/__tests__/offline-evidence.integration.test.d.ts.map +1 -0
- package/dist/__tests__/owner-chain.integration.test.d.ts +2 -0
- package/dist/__tests__/owner-chain.integration.test.d.ts.map +1 -0
- package/dist/__tests__/pack-v2-fixture-migration.test.d.ts +2 -0
- package/dist/__tests__/pack-v2-fixture-migration.test.d.ts.map +1 -0
- package/dist/__tests__/pack-v2-schema.test.d.ts +2 -0
- package/dist/__tests__/pack-v2-schema.test.d.ts.map +1 -0
- package/dist/__tests__/pack.unit.test.d.ts +2 -0
- package/dist/__tests__/pack.unit.test.d.ts.map +1 -0
- package/dist/__tests__/package-finalizer.contract.test.d.ts +2 -0
- package/dist/__tests__/package-finalizer.contract.test.d.ts.map +1 -0
- package/dist/__tests__/producer-contract-schema.unit.test.d.ts +2 -0
- package/dist/__tests__/producer-contract-schema.unit.test.d.ts.map +1 -0
- package/dist/__tests__/resolve-asset-source.test.d.ts +2 -0
- package/dist/__tests__/resolve-asset-source.test.d.ts.map +1 -0
- package/dist/__tests__/runtime-projection.unit.test.d.ts +2 -0
- package/dist/__tests__/runtime-projection.unit.test.d.ts.map +1 -0
- package/dist/__tests__/runtime.browser.test.d.ts +2 -0
- package/dist/__tests__/runtime.browser.test.d.ts.map +1 -0
- package/dist/__tests__/scanner-inventory.contract.test.d.ts +2 -0
- package/dist/__tests__/scanner-inventory.contract.test.d.ts.map +1 -0
- package/dist/__tests__/scanner-inventory.test.d.ts +2 -0
- package/dist/__tests__/scanner-inventory.test.d.ts.map +1 -0
- package/dist/__tests__/scanner-mount-cycle.test.d.ts +2 -0
- package/dist/__tests__/scanner-mount-cycle.test.d.ts.map +1 -0
- package/dist/__tests__/scriptable-pack-cli.integration.test.d.ts +2 -0
- package/dist/__tests__/scriptable-pack-cli.integration.test.d.ts.map +1 -0
- package/dist/__tests__/scriptable-pack-ddc-key.unit.test.d.ts +2 -0
- package/dist/__tests__/scriptable-pack-ddc-key.unit.test.d.ts.map +1 -0
- package/dist/__tests__/scriptable-pack.test-d.d.ts +2 -0
- package/dist/__tests__/scriptable-pack.test-d.d.ts.map +1 -0
- package/dist/__tests__/scriptable-pack.unit.test.d.ts +2 -0
- package/dist/__tests__/scriptable-pack.unit.test.d.ts.map +1 -0
- package/dist/__tests__/topology-actions.unit.test.d.ts +2 -0
- package/dist/__tests__/topology-actions.unit.test.d.ts.map +1 -0
- package/dist/__tests__/topology.unit.test.d.ts +2 -0
- package/dist/__tests__/topology.unit.test.d.ts.map +1 -0
- package/dist/artifact-path.d.ts +9 -0
- package/dist/artifact-path.d.ts.map +1 -0
- package/dist/artifact-path.mjs +53 -0
- package/dist/artifact-path.mjs.map +1 -0
- package/dist/atlas/run-atlas.d.ts +8 -0
- package/dist/atlas/run-atlas.d.ts.map +1 -0
- package/dist/atlas/shelf-pack.d.ts +55 -0
- package/dist/atlas/shelf-pack.d.ts.map +1 -0
- package/dist/bridge.d.ts +2 -0
- package/dist/bridge.d.ts.map +1 -0
- package/dist/bridge.mjs +3 -0
- package/dist/bridge.mjs.map +1 -0
- package/dist/build.d.ts +19 -0
- package/dist/build.d.ts.map +1 -0
- package/dist/build.mjs +10203 -0
- package/dist/build.mjs.map +1 -0
- package/dist/builtin.d.ts +44 -0
- package/dist/builtin.d.ts.map +1 -0
- package/dist/builtin.mjs +141 -0
- package/dist/builtin.mjs.map +1 -0
- package/dist/catalog-builder.d.ts +43 -0
- package/dist/catalog-builder.d.ts.map +1 -0
- package/dist/catalog-delta.d.ts +11 -0
- package/dist/catalog-delta.d.ts.map +1 -0
- package/dist/catalog-projection.d.ts +91 -0
- package/dist/catalog-projection.d.ts.map +1 -0
- package/dist/cli-asset.d.ts +22 -0
- package/dist/cli-asset.d.ts.map +1 -0
- package/dist/cli-asset.mjs +9697 -0
- package/dist/cli-asset.mjs.map +1 -0
- package/dist/config.d.ts +6 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.mjs +29 -0
- package/dist/config.mjs.map +1 -0
- package/dist/deriveAssetName.d.ts +15 -0
- package/dist/deriveAssetName.d.ts.map +1 -0
- package/dist/errors.d.ts +30 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.mjs +19 -0
- package/dist/errors.mjs.map +1 -0
- package/dist/evidence/material-cook.d.ts +92 -0
- package/dist/evidence/material-cook.d.ts.map +1 -0
- package/dist/evidence/offline-evidence.d.ts +25 -0
- package/dist/evidence/offline-evidence.d.ts.map +1 -0
- package/dist/evidence/source-inventory.d.ts +29 -0
- package/dist/evidence/source-inventory.d.ts.map +1 -0
- package/dist/guid.d.ts +45 -0
- package/dist/guid.d.ts.map +1 -0
- package/dist/guid.mjs +94 -0
- package/dist/guid.mjs.map +1 -0
- package/dist/index.d.ts +15 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.mjs +8612 -0
- package/dist/index.mjs.map +1 -0
- package/dist/material/artifact-writer.d.ts +14 -0
- package/dist/material/artifact-writer.d.ts.map +1 -0
- package/dist/material-cook.d.ts +2 -0
- package/dist/material-cook.d.ts.map +1 -0
- package/dist/material-cook.mjs +248 -0
- package/dist/material-cook.mjs.map +1 -0
- package/dist/mesh-bin-contract.d.ts +36 -0
- package/dist/mesh-bin-contract.d.ts.map +1 -0
- package/dist/mesh-bin-contract.mjs +96 -0
- package/dist/mesh-bin-contract.mjs.map +1 -0
- package/dist/name.mjs +22 -0
- package/dist/name.mjs.map +1 -0
- package/dist/native-cooker-registry.d.ts +47 -0
- package/dist/native-cooker-registry.d.ts.map +1 -0
- package/dist/native-cooker.d.ts +3 -0
- package/dist/native-cooker.d.ts.map +1 -0
- package/dist/native-cooker.mjs +142 -0
- package/dist/native-cooker.mjs.map +1 -0
- package/dist/package-finalizer.d.ts +121 -0
- package/dist/package-finalizer.d.ts.map +1 -0
- package/dist/producer-contract.d.ts +19 -0
- package/dist/producer-contract.d.ts.map +1 -0
- package/dist/resolve-asset-source.d.ts +4 -0
- package/dist/resolve-asset-source.d.ts.map +1 -0
- package/dist/resolve-asset-source.mjs +109 -0
- package/dist/resolve-asset-source.mjs.map +1 -0
- package/dist/runtime-projection.d.ts +14 -0
- package/dist/runtime-projection.d.ts.map +1 -0
- package/dist/runtime-publication.d.ts +44 -0
- package/dist/runtime-publication.d.ts.map +1 -0
- package/dist/runtime.d.ts +8 -0
- package/dist/runtime.d.ts.map +1 -0
- package/dist/runtime.mjs +7261 -0
- package/dist/runtime.mjs.map +1 -0
- package/dist/scanner.d.ts +113 -0
- package/dist/scanner.d.ts.map +1 -0
- package/dist/scanner.mjs +8819 -0
- package/dist/scanner.mjs.map +1 -0
- package/dist/schema-compiled.d.ts +12 -0
- package/dist/schema-compiled.d.ts.map +1 -0
- package/dist/schema.mjs +7369 -0
- package/dist/schema.mjs.map +1 -0
- package/dist/scriptable-pack-node.d.ts +62 -0
- package/dist/scriptable-pack-node.d.ts.map +1 -0
- package/dist/scriptable-pack-node.mjs +1674 -0
- package/dist/scriptable-pack-node.mjs.map +1 -0
- package/dist/scriptable-pack-worker.d.ts +2 -0
- package/dist/scriptable-pack-worker.d.ts.map +1 -0
- package/dist/scriptable-pack-worker.mjs +224 -0
- package/dist/scriptable-pack-worker.mjs.map +1 -0
- package/dist/scriptable-pack.d.ts +558 -0
- package/dist/scriptable-pack.d.ts.map +1 -0
- package/dist/scriptable-pack.mjs +672 -0
- package/dist/scriptable-pack.mjs.map +1 -0
- package/dist/topology.d.ts +10 -0
- package/dist/topology.d.ts.map +1 -0
- package/package.json +154 -0
- package/schema/meta.schema.json +173 -0
- package/schema/pack.schema.json +232 -0
- package/src/__tests__/ai-recovery.unit.test.ts +114 -0
- package/src/__tests__/artifact-path.test.ts +41 -0
- package/src/__tests__/asset-evidence-error-hints.test.ts +46 -0
- package/src/__tests__/asset-evidence-lifecycle.test.ts +104 -0
- package/src/__tests__/asset-evidence-schema.test.ts +86 -0
- package/src/__tests__/atlas-cli-region-mismatch.test.ts +134 -0
- package/src/__tests__/atlas-error-code-owner.test-d.ts +23 -0
- package/src/__tests__/cli-asset-evidence.integration.test.ts +172 -0
- package/src/__tests__/cli.unit.test.ts +448 -0
- package/src/__tests__/evidence-source-inventory.unit.test.ts +37 -0
- package/src/__tests__/guid-collision.unit.test.ts +112 -0
- package/src/__tests__/guid-validator-surface.unit.test.ts +20 -0
- package/src/__tests__/load-asset-config.test.ts +121 -0
- package/src/__tests__/material-cook-dependencies.unit.test.ts +112 -0
- package/src/__tests__/material-cook-receipt.unit.test.ts +148 -0
- package/src/__tests__/material-cook-schema.unit.test.ts +152 -0
- package/src/__tests__/mesh-bin-consumer-surface.unit.test.ts +22 -0
- package/src/__tests__/mesh-bin-contract.unit.test.ts +32 -0
- package/src/__tests__/meta-schema-optional.test.ts +116 -0
- package/src/__tests__/meta-source-overrides.unit.test.ts +71 -0
- package/src/__tests__/native-cooker-registry.test.ts +64 -0
- package/src/__tests__/offline-evidence-artifact-verification-owner.test-d.ts +64 -0
- package/src/__tests__/offline-evidence.integration.test.ts +106 -0
- package/src/__tests__/owner-chain.integration.test.ts +78 -0
- package/src/__tests__/pack-v2-fixture-migration.test.ts +87 -0
- package/src/__tests__/pack-v2-schema.test.ts +142 -0
- package/src/__tests__/pack.unit.test.ts +2218 -0
- package/src/__tests__/package-finalizer.contract.test.ts +105 -0
- package/src/__tests__/producer-contract-schema.unit.test.ts +92 -0
- package/src/__tests__/resolve-asset-source.test.ts +121 -0
- package/src/__tests__/runtime-projection.unit.test.ts +87 -0
- package/src/__tests__/runtime.browser.test.ts +15 -0
- package/src/__tests__/scanner-inventory.contract.test.ts +167 -0
- package/src/__tests__/scanner-inventory.test.ts +76 -0
- package/src/__tests__/scanner-mount-cycle.test.ts +232 -0
- package/src/__tests__/scriptable-pack-cli.integration.test.ts +47 -0
- package/src/__tests__/scriptable-pack-ddc-key.unit.test.ts +63 -0
- package/src/__tests__/scriptable-pack.test-d.ts +131 -0
- package/src/__tests__/scriptable-pack.unit.test.ts +789 -0
- package/src/__tests__/topology-actions.unit.test.ts +94 -0
- package/src/__tests__/topology.unit.test.ts +85 -0
- package/src/artifact-path.ts +69 -0
- package/src/atlas/run-atlas.ts +358 -0
- package/src/atlas/shelf-pack.ts +172 -0
- package/src/atlas/upng-ambient.d.ts +13 -0
- package/src/bridge.ts +2 -0
- package/src/build.ts +139 -0
- package/src/builtin.ts +117 -0
- package/src/catalog-builder.ts +313 -0
- package/src/catalog-delta.ts +189 -0
- package/src/catalog-projection.ts +344 -0
- package/src/cli-asset.ts +586 -0
- package/src/config.ts +36 -0
- package/src/deriveAssetName.ts +42 -0
- package/src/errors.ts +47 -0
- package/src/evidence/material-cook.ts +411 -0
- package/src/evidence/offline-evidence.ts +90 -0
- package/src/evidence/source-inventory.ts +193 -0
- package/src/guid.ts +99 -0
- package/src/index.ts +108 -0
- package/src/material/artifact-writer.ts +26 -0
- package/src/material-cook.ts +15 -0
- package/src/mesh-bin-contract.ts +150 -0
- package/src/native-cooker-registry.ts +235 -0
- package/src/native-cooker.ts +2 -0
- package/src/package-finalizer.ts +394 -0
- package/src/producer-contract.ts +277 -0
- package/src/resolve-asset-source.ts +88 -0
- package/src/runtime-projection.ts +100 -0
- package/src/runtime-publication.ts +190 -0
- package/src/runtime.ts +23 -0
- package/src/scanner.ts +715 -0
- package/src/schema/material-cook.schema.json +119 -0
- package/src/schema-compiled.ts +238 -0
- package/src/scriptable-pack-node.ts +1394 -0
- package/src/scriptable-pack-worker.ts +308 -0
- package/src/scriptable-pack.ts +1006 -0
- package/src/topology.ts +157 -0
|
@@ -0,0 +1,142 @@
|
|
|
1
|
+
import { createHash } from 'crypto';
|
|
2
|
+
import { ok, err } from '@forgeax/engine-types';
|
|
3
|
+
|
|
4
|
+
// src/native-cooker-registry.ts
|
|
5
|
+
function canonicalize(value) {
|
|
6
|
+
if (value instanceof Uint8Array) return Buffer.from(value).toString("base64");
|
|
7
|
+
if (Array.isArray(value)) return value.map(canonicalize);
|
|
8
|
+
if (typeof value !== "object" || value === null) return value;
|
|
9
|
+
return Object.fromEntries(
|
|
10
|
+
Object.entries(value).sort(([left], [right]) => left.localeCompare(right)).map(([key, nested]) => [key, canonicalize(nested)])
|
|
11
|
+
);
|
|
12
|
+
}
|
|
13
|
+
function digestDraft(draft) {
|
|
14
|
+
const bytes = JSON.stringify(
|
|
15
|
+
canonicalize({
|
|
16
|
+
guid: draft.guid,
|
|
17
|
+
payload: draft.payload,
|
|
18
|
+
refs: draft.refs,
|
|
19
|
+
artifacts: draft.artifacts
|
|
20
|
+
})
|
|
21
|
+
);
|
|
22
|
+
return `sha256:${createHash("sha256").update(bytes).digest("hex")}`;
|
|
23
|
+
}
|
|
24
|
+
function failure(key, detail) {
|
|
25
|
+
return err({
|
|
26
|
+
stage: "native-cook",
|
|
27
|
+
code: "native-cook-failed",
|
|
28
|
+
expected: "a registered native cooker to produce a complete draft",
|
|
29
|
+
hint: "register the cooker or repair its draft, then rerun recovery",
|
|
30
|
+
detail,
|
|
31
|
+
recovery: { action: `rerun native cooker ${key}`, retryable: true }
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
function transactionFailure(key, reason) {
|
|
35
|
+
return failure(key, { guid: "unknown", producer: reason });
|
|
36
|
+
}
|
|
37
|
+
function recovered(key, previous) {
|
|
38
|
+
return {
|
|
39
|
+
...previous,
|
|
40
|
+
status: "recovered",
|
|
41
|
+
lastKnownGood: previous.draft,
|
|
42
|
+
candidateGeneration: previous.generation + 1,
|
|
43
|
+
lastKnownGoodGeneration: previous.generation,
|
|
44
|
+
recoveryHint: `repair ${key} and submit a new candidate generation`
|
|
45
|
+
};
|
|
46
|
+
}
|
|
47
|
+
var NativeCookerRegistry = class {
|
|
48
|
+
cookers = /* @__PURE__ */ new Map();
|
|
49
|
+
register(cooker) {
|
|
50
|
+
if (typeof cooker.key !== "string" || cooker.key.length === 0) {
|
|
51
|
+
throw new TypeError("NativeCookerRegistry.register: key must be a non-empty string");
|
|
52
|
+
}
|
|
53
|
+
if (typeof cooker.cook !== "function") {
|
|
54
|
+
throw new TypeError(`NativeCookerRegistry.register: cooker ${cooker.key} must expose cook`);
|
|
55
|
+
}
|
|
56
|
+
this.cookers.set(cooker.key, cooker);
|
|
57
|
+
}
|
|
58
|
+
get(key) {
|
|
59
|
+
return this.cookers.get(key);
|
|
60
|
+
}
|
|
61
|
+
registeredCookers() {
|
|
62
|
+
return [...this.cookers.keys()];
|
|
63
|
+
}
|
|
64
|
+
async runDraft(key, input) {
|
|
65
|
+
const cooker = this.cookers.get(key);
|
|
66
|
+
if (cooker === void 0) {
|
|
67
|
+
return failure(key, { guid: "unknown", producer: key });
|
|
68
|
+
}
|
|
69
|
+
let draft;
|
|
70
|
+
try {
|
|
71
|
+
const typedInput = cooker.discover === void 0 ? input : await cooker.discover(input);
|
|
72
|
+
draft = await cooker.cook(typedInput);
|
|
73
|
+
} catch (error) {
|
|
74
|
+
return failure(key, { guid: "unknown", producer: String(error) });
|
|
75
|
+
}
|
|
76
|
+
if (draft.guid.length === 0 || draft.inputFingerprint.length === 0 || !Array.isArray(draft.refs) || typeof draft.payload !== "object" || draft.payload === null || typeof draft.artifacts !== "object" || draft.artifacts === null || Object.entries(draft.artifacts).some(
|
|
77
|
+
([, artifact]) => artifact === null || typeof artifact !== "object" || typeof artifact.mediaType !== "string" || artifact.mediaType.length === 0 || !(artifact.bytes instanceof Uint8Array)
|
|
78
|
+
)) {
|
|
79
|
+
return failure(key, { guid: draft.guid || "unknown", producer: key });
|
|
80
|
+
}
|
|
81
|
+
return ok(draft);
|
|
82
|
+
}
|
|
83
|
+
async run(key, input) {
|
|
84
|
+
const draftResult = await this.runDraft(key, input);
|
|
85
|
+
if (!draftResult.ok) return draftResult;
|
|
86
|
+
const draft = draftResult.value;
|
|
87
|
+
const digest = digestDraft(draft);
|
|
88
|
+
const artifacts = {};
|
|
89
|
+
for (const [path, artifact] of Object.entries(draft.artifacts)) {
|
|
90
|
+
artifacts[path] = {
|
|
91
|
+
path,
|
|
92
|
+
mediaType: artifact.mediaType,
|
|
93
|
+
...artifact.assetCodec === void 0 ? {} : { assetCodec: artifact.assetCodec },
|
|
94
|
+
byteLength: artifact.bytes.byteLength
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
const receipt = {
|
|
98
|
+
guid: draft.guid,
|
|
99
|
+
origin: "authoredPack",
|
|
100
|
+
status: "succeeded",
|
|
101
|
+
inputFingerprint: draft.inputFingerprint,
|
|
102
|
+
outputDigest: digest
|
|
103
|
+
};
|
|
104
|
+
const product = {
|
|
105
|
+
guid: draft.guid,
|
|
106
|
+
payload: draft.payload,
|
|
107
|
+
refs: draft.refs,
|
|
108
|
+
artifacts,
|
|
109
|
+
digest,
|
|
110
|
+
receipt
|
|
111
|
+
};
|
|
112
|
+
return ok(product);
|
|
113
|
+
}
|
|
114
|
+
async runTransaction(options) {
|
|
115
|
+
const candidate = await this.runDraft(options.key, options.input);
|
|
116
|
+
if (!candidate.ok) {
|
|
117
|
+
return options.previous === void 0 ? candidate : ok(recovered(options.key, options.previous));
|
|
118
|
+
}
|
|
119
|
+
const invalidReason = options.validate?.(candidate.value);
|
|
120
|
+
if (invalidReason !== void 0) {
|
|
121
|
+
return options.previous === void 0 ? transactionFailure(options.key, invalidReason) : ok(recovered(options.key, options.previous));
|
|
122
|
+
}
|
|
123
|
+
const generation = (options.previous?.generation ?? 0) + 1;
|
|
124
|
+
try {
|
|
125
|
+
await options.publish?.(candidate.value, generation);
|
|
126
|
+
} catch {
|
|
127
|
+
return options.previous === void 0 ? transactionFailure(options.key, "atomic producer publication failed") : ok(recovered(options.key, options.previous));
|
|
128
|
+
}
|
|
129
|
+
return ok({
|
|
130
|
+
draft: candidate.value,
|
|
131
|
+
generation,
|
|
132
|
+
status: "committed",
|
|
133
|
+
lastKnownGood: candidate.value,
|
|
134
|
+
candidateGeneration: generation,
|
|
135
|
+
lastKnownGoodGeneration: generation
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
};
|
|
139
|
+
|
|
140
|
+
export { NativeCookerRegistry };
|
|
141
|
+
//# sourceMappingURL=native-cooker.mjs.map
|
|
142
|
+
//# sourceMappingURL=native-cooker.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/native-cooker-registry.ts"],"names":[],"mappings":"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","file":"native-cooker.mjs","sourcesContent":["import { createHash } from 'node:crypto';\nimport type {\n ArtifactDescriptor,\n AssetCodec,\n AssetStageError,\n CookProduct,\n Result,\n} from '@forgeax/engine-types';\nimport { err, ok } from '@forgeax/engine-types';\n\nexport interface NativeCookArtifact {\n readonly mediaType: string;\n readonly assetCodec?: AssetCodec;\n readonly bytes: Uint8Array;\n}\n\nexport interface NativeCookDraft<P = unknown> {\n readonly guid: string;\n readonly payload: P;\n readonly refs: readonly string[];\n readonly artifacts: Readonly<Record<string, NativeCookArtifact>>;\n readonly inputFingerprint: string;\n}\n\nexport interface NativeCooker<P = unknown, I = unknown> {\n readonly key: string;\n readonly discover?: (input: unknown) => I | Promise<I>;\n cook(input: I): NativeCookDraft<P> | Promise<NativeCookDraft<P>>;\n}\n\nexport interface NativeCookTransactionSnapshot<P = unknown> {\n readonly draft: NativeCookDraft<P>;\n readonly generation: number;\n}\n\nexport interface NativeCookTransactionOptions<P = unknown, I = unknown> {\n readonly key: string;\n readonly input: I;\n readonly previous?: NativeCookTransactionSnapshot<P>;\n readonly validate?: (draft: NativeCookDraft<P>) => string | undefined;\n readonly publish?: (draft: NativeCookDraft<P>, generation: number) => void | Promise<void>;\n}\n\nexport interface NativeCookTransactionResult<P = unknown> extends NativeCookTransactionSnapshot<P> {\n readonly status: 'committed' | 'recovered';\n readonly lastKnownGood: NativeCookDraft<P>;\n readonly candidateGeneration: number;\n readonly lastKnownGoodGeneration: number;\n readonly recoveryHint?: string;\n}\n\nfunction canonicalize(value: unknown): unknown {\n if (value instanceof Uint8Array) return Buffer.from(value).toString('base64');\n if (Array.isArray(value)) return value.map(canonicalize);\n if (typeof value !== 'object' || value === null) return value;\n return Object.fromEntries(\n Object.entries(value)\n .sort(([left], [right]) => left.localeCompare(right))\n .map(([key, nested]) => [key, canonicalize(nested)]),\n );\n}\n\nfunction digestDraft<P>(draft: NativeCookDraft<P>): string {\n const bytes = JSON.stringify(\n canonicalize({\n guid: draft.guid,\n payload: draft.payload,\n refs: draft.refs,\n artifacts: draft.artifacts,\n }),\n );\n return `sha256:${createHash('sha256').update(bytes).digest('hex')}`;\n}\n\ntype NativeCookErrorDetail = Extract<\n AssetStageError['detail'],\n { readonly guid: string; readonly producer: string }\n>;\n\nfunction failure(key: string, detail: NativeCookErrorDetail): Result<never, AssetStageError> {\n return err({\n stage: 'native-cook',\n code: 'native-cook-failed',\n expected: 'a registered native cooker to produce a complete draft',\n hint: 'register the cooker or repair its draft, then rerun recovery',\n detail,\n recovery: { action: `rerun native cooker ${key}`, retryable: true },\n });\n}\n\nfunction transactionFailure(key: string, reason: string): Result<never, AssetStageError> {\n return failure(key, { guid: 'unknown', producer: reason });\n}\n\nfunction recovered<P>(\n key: string,\n previous: NativeCookTransactionSnapshot<P>,\n): NativeCookTransactionResult<P> {\n return {\n ...previous,\n status: 'recovered',\n lastKnownGood: previous.draft,\n candidateGeneration: previous.generation + 1,\n lastKnownGoodGeneration: previous.generation,\n recoveryHint: `repair ${key} and submit a new candidate generation`,\n };\n}\n\n/** Injectable build-time table for native authored Pack producers. */\nexport class NativeCookerRegistry {\n private readonly cookers = new Map<string, NativeCooker>();\n\n register(cooker: NativeCooker): void {\n if (typeof cooker.key !== 'string' || cooker.key.length === 0) {\n throw new TypeError('NativeCookerRegistry.register: key must be a non-empty string');\n }\n if (typeof cooker.cook !== 'function') {\n throw new TypeError(`NativeCookerRegistry.register: cooker ${cooker.key} must expose cook`);\n }\n this.cookers.set(cooker.key, cooker);\n }\n\n get(key: string): NativeCooker | undefined {\n return this.cookers.get(key);\n }\n\n registeredCookers(): readonly string[] {\n return [...this.cookers.keys()];\n }\n\n async runDraft<P = unknown, I = unknown>(\n key: string,\n input: I,\n ): Promise<Result<NativeCookDraft<P>, AssetStageError>> {\n const cooker = this.cookers.get(key) as NativeCooker<P, I> | undefined;\n if (cooker === undefined) {\n return failure(key, { guid: 'unknown', producer: key });\n }\n let draft: NativeCookDraft<P>;\n try {\n const typedInput = cooker.discover === undefined ? input : await cooker.discover(input);\n draft = await cooker.cook(typedInput);\n } catch (error) {\n return failure(key, { guid: 'unknown', producer: String(error) });\n }\n if (\n draft.guid.length === 0 ||\n draft.inputFingerprint.length === 0 ||\n !Array.isArray(draft.refs) ||\n typeof draft.payload !== 'object' ||\n draft.payload === null ||\n typeof draft.artifacts !== 'object' ||\n draft.artifacts === null ||\n Object.entries(draft.artifacts).some(\n ([, artifact]) =>\n artifact === null ||\n typeof artifact !== 'object' ||\n typeof artifact.mediaType !== 'string' ||\n artifact.mediaType.length === 0 ||\n !(artifact.bytes instanceof Uint8Array),\n )\n ) {\n return failure(key, { guid: draft.guid || 'unknown', producer: key });\n }\n return ok(draft);\n }\n\n async run<P = unknown, I = unknown>(\n key: string,\n input: I,\n ): Promise<Result<CookProduct<P>, AssetStageError>> {\n const draftResult = await this.runDraft<P, I>(key, input);\n if (!draftResult.ok) return draftResult;\n const draft = draftResult.value;\n const digest = digestDraft(draft);\n const artifacts: Record<string, ArtifactDescriptor> = {};\n for (const [path, artifact] of Object.entries(draft.artifacts)) {\n artifacts[path] = {\n path,\n mediaType: artifact.mediaType,\n ...(artifact.assetCodec === undefined ? {} : { assetCodec: artifact.assetCodec }),\n byteLength: artifact.bytes.byteLength,\n };\n }\n const receipt = {\n guid: draft.guid,\n origin: 'authoredPack' as const,\n status: 'succeeded' as const,\n inputFingerprint: draft.inputFingerprint,\n outputDigest: digest,\n };\n const product: CookProduct<P> = {\n guid: draft.guid,\n payload: draft.payload,\n refs: draft.refs,\n artifacts,\n digest,\n receipt,\n };\n return ok(product);\n }\n\n async runTransaction<P = unknown, I = unknown>(\n options: NativeCookTransactionOptions<P, I>,\n ): Promise<Result<NativeCookTransactionResult<P>, AssetStageError>> {\n const candidate = await this.runDraft<P, I>(options.key, options.input);\n if (!candidate.ok) {\n return options.previous === undefined\n ? candidate\n : ok(recovered(options.key, options.previous));\n }\n const invalidReason = options.validate?.(candidate.value);\n if (invalidReason !== undefined) {\n return options.previous === undefined\n ? transactionFailure(options.key, invalidReason)\n : ok(recovered(options.key, options.previous));\n }\n const generation = (options.previous?.generation ?? 0) + 1;\n try {\n await options.publish?.(candidate.value, generation);\n } catch {\n return options.previous === undefined\n ? transactionFailure(options.key, 'atomic producer publication failed')\n : ok(recovered(options.key, options.previous));\n }\n return ok({\n draft: candidate.value,\n generation,\n status: 'committed',\n lastKnownGood: candidate.value,\n candidateGeneration: generation,\n lastKnownGoodGeneration: generation,\n });\n }\n}\n"]}
|
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
import type { AssetCodec, AssetRelation, CookReceipt } from '@forgeax/engine-types';
|
|
2
|
+
export interface PackageArtifactBody {
|
|
3
|
+
readonly mediaType: string;
|
|
4
|
+
readonly assetCodec?: AssetCodec;
|
|
5
|
+
readonly bytes: Uint8Array;
|
|
6
|
+
}
|
|
7
|
+
export interface PackageProductAsset {
|
|
8
|
+
readonly guid: string;
|
|
9
|
+
readonly kind: string;
|
|
10
|
+
readonly name?: string;
|
|
11
|
+
readonly payload: Readonly<Record<string, unknown>>;
|
|
12
|
+
readonly refs: readonly string[];
|
|
13
|
+
readonly artifacts: Readonly<Record<string, PackageArtifactBody>>;
|
|
14
|
+
}
|
|
15
|
+
export interface PackageProduct {
|
|
16
|
+
readonly assets: readonly PackageProductAsset[];
|
|
17
|
+
readonly receipts: readonly CookReceipt[];
|
|
18
|
+
readonly diagnostics: readonly unknown[];
|
|
19
|
+
readonly sourceRevision: string;
|
|
20
|
+
readonly sourceKey?: string;
|
|
21
|
+
}
|
|
22
|
+
/** Minimal authored Pack v1/v2 shape consumed by the file transport seam. */
|
|
23
|
+
export interface AuthoredPackAssetInput {
|
|
24
|
+
readonly guid: string;
|
|
25
|
+
readonly kind: string;
|
|
26
|
+
readonly name?: string;
|
|
27
|
+
readonly execution?: 'direct' | 'cooked';
|
|
28
|
+
readonly sourceKey?: string;
|
|
29
|
+
readonly sourceIndex?: number;
|
|
30
|
+
readonly relations?: readonly AssetRelation[];
|
|
31
|
+
readonly payload: Record<string, unknown>;
|
|
32
|
+
readonly refs?: readonly string[];
|
|
33
|
+
readonly artifacts?: Readonly<Record<string, unknown>>;
|
|
34
|
+
}
|
|
35
|
+
export interface AuthoredPackInput {
|
|
36
|
+
readonly schemaVersion?: string;
|
|
37
|
+
readonly assets?: readonly AuthoredPackAssetInput[];
|
|
38
|
+
}
|
|
39
|
+
export interface PackageDocumentArtifact {
|
|
40
|
+
readonly path: string;
|
|
41
|
+
readonly mediaType: string;
|
|
42
|
+
readonly assetCodec?: AssetCodec;
|
|
43
|
+
readonly byteLength: number;
|
|
44
|
+
readonly integrity: {
|
|
45
|
+
readonly algorithm: 'sha256';
|
|
46
|
+
readonly digest: string;
|
|
47
|
+
};
|
|
48
|
+
}
|
|
49
|
+
export interface PackageDocumentAsset {
|
|
50
|
+
readonly guid: string;
|
|
51
|
+
readonly kind: string;
|
|
52
|
+
readonly name?: string;
|
|
53
|
+
readonly payload: Record<string, unknown>;
|
|
54
|
+
readonly refs: readonly string[];
|
|
55
|
+
readonly artifacts: Readonly<Record<string, PackageDocumentArtifact>>;
|
|
56
|
+
}
|
|
57
|
+
export interface PackageDocument {
|
|
58
|
+
readonly schemaVersion: '2.0.0';
|
|
59
|
+
readonly kind: 'internal-text-package';
|
|
60
|
+
readonly assets: readonly PackageDocumentAsset[];
|
|
61
|
+
}
|
|
62
|
+
/** Upgrade the legacy authored Pack envelope at the Pack schema boundary. */
|
|
63
|
+
export declare function upgradeLegacyAuthoredPack(pack: AuthoredPackInput): AuthoredPackInput;
|
|
64
|
+
export interface PackageFinalizePolicy {
|
|
65
|
+
readonly base: string;
|
|
66
|
+
readonly packagePath: string;
|
|
67
|
+
readonly artifactPath: (guid: string, localKey: string) => string;
|
|
68
|
+
readonly sink?: (path: string, bytes: Uint8Array) => void | Promise<void>;
|
|
69
|
+
}
|
|
70
|
+
export interface FinalizedPackageProduct {
|
|
71
|
+
readonly pack: PackageDocument;
|
|
72
|
+
readonly packageUrl: string;
|
|
73
|
+
readonly digest: string;
|
|
74
|
+
readonly receipts: readonly CookReceipt[];
|
|
75
|
+
readonly diagnostics: readonly unknown[];
|
|
76
|
+
readonly sourceRevision: string;
|
|
77
|
+
readonly sourceKey?: string;
|
|
78
|
+
}
|
|
79
|
+
interface PackageTransportSource {
|
|
80
|
+
readonly assets: readonly PackageProduct['assets'][number][];
|
|
81
|
+
readonly receipts?: readonly CookReceipt[];
|
|
82
|
+
readonly diagnostics?: readonly unknown[];
|
|
83
|
+
readonly sourceKey?: string;
|
|
84
|
+
}
|
|
85
|
+
export interface PackageFinalizerError {
|
|
86
|
+
readonly code: 'duplicate-guid' | 'missing-source-revision' | 'missing-receipt' | 'invalid-artifact';
|
|
87
|
+
readonly expected: string;
|
|
88
|
+
readonly hint: string;
|
|
89
|
+
readonly detail: {
|
|
90
|
+
readonly guid?: string;
|
|
91
|
+
readonly key?: string;
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
export type PackageFinalizeResult = {
|
|
95
|
+
readonly ok: true;
|
|
96
|
+
readonly value: FinalizedPackageProduct;
|
|
97
|
+
} | {
|
|
98
|
+
readonly ok: false;
|
|
99
|
+
readonly error: PackageFinalizerError;
|
|
100
|
+
};
|
|
101
|
+
/** Finalize a complete producer product without owning producer-specific policy. */
|
|
102
|
+
export declare function finalizePackageProduct(product: PackageProduct, policy: PackageFinalizePolicy): Promise<PackageFinalizeResult>;
|
|
103
|
+
/** Finalize a product-shaped source with the deterministic transport revision. */
|
|
104
|
+
export declare function finalizePackageTransportSource(input: PackageTransportSource, policy: PackageFinalizePolicy): Promise<{
|
|
105
|
+
pack: PackageDocument;
|
|
106
|
+
packageUrl: string;
|
|
107
|
+
artifacts: {
|
|
108
|
+
bytes: Uint8Array<ArrayBufferLike>;
|
|
109
|
+
assetCodec?: AssetCodec;
|
|
110
|
+
guid: string;
|
|
111
|
+
localKey: string;
|
|
112
|
+
path: string;
|
|
113
|
+
mediaType: string;
|
|
114
|
+
}[];
|
|
115
|
+
digest: string;
|
|
116
|
+
sourceRevision: string;
|
|
117
|
+
semantic: string;
|
|
118
|
+
}>;
|
|
119
|
+
export declare function packageTransportRevision(value: unknown): string;
|
|
120
|
+
export {};
|
|
121
|
+
//# sourceMappingURL=package-finalizer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"package-finalizer.d.ts","sourceRoot":"","sources":["../src/package-finalizer.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import type { ImportedOutputDeclaration, ProducerContractResult } from '@forgeax/engine-types';
|
|
2
|
+
type ProducerObject = Record<string, unknown>;
|
|
3
|
+
/**
|
|
4
|
+
* Validate one package or imported-output producer declaration.
|
|
5
|
+
*
|
|
6
|
+
* The accepted fields mirror the engine-types POD contract. This function
|
|
7
|
+
* validates that schema without creating a second schema or interpreting
|
|
8
|
+
* diagnostic messages.
|
|
9
|
+
*/
|
|
10
|
+
export declare function validateProducerContract(value: unknown): ProducerContractResult<ProducerObject>;
|
|
11
|
+
/**
|
|
12
|
+
* Validate output topology without ever treating `sourceIndex` as identity.
|
|
13
|
+
*
|
|
14
|
+
* AI-readable callers should use the discriminated result and its structured
|
|
15
|
+
* `code`, `expected`, `actual`, and `hint` fields for recovery decisions.
|
|
16
|
+
*/
|
|
17
|
+
export declare function validateProducerOutputs(outputs: readonly ImportedOutputDeclaration[]): ProducerContractResult<readonly ImportedOutputDeclaration[]>;
|
|
18
|
+
export {};
|
|
19
|
+
//# sourceMappingURL=producer-contract.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"producer-contract.d.ts","sourceRoot":"","sources":["../src/producer-contract.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAEV,yBAAyB,EAEzB,sBAAsB,EAEvB,MAAM,uBAAuB,CAAC;AAG/B,KAAK,cAAc,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AA4I9C;;;;;;GAMG;AACH,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,OAAO,GAAG,sBAAsB,CAAC,cAAc,CAAC,CAiF/F;AAED;;;;;GAKG;AACH,wBAAgB,uBAAuB,CACrC,OAAO,EAAE,SAAS,yBAAyB,EAAE,GAC5C,sBAAsB,CAAC,SAAS,yBAAyB,EAAE,CAAC,CA6B9D"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { Result } from '@forgeax/engine-types';
|
|
2
|
+
import { PackError } from './errors.js';
|
|
3
|
+
export declare function resolveAssetSource(metaPath: string, source: string | undefined, paths: Record<string, string>): Result<string, PackError>;
|
|
4
|
+
//# sourceMappingURL=resolve-asset-source.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"resolve-asset-source.d.ts","sourceRoot":"","sources":["../src/resolve-asset-source.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,uBAAuB,CAAC;AAGpD,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAaxC,wBAAgB,kBAAkB,CAChC,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,GAAG,SAAS,EAC1B,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAC5B,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,CAkE3B"}
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
import { dirname, resolve, posix } from 'path';
|
|
2
|
+
import { ok, err, PACK_ERROR_HINTS } from '@forgeax/engine-types';
|
|
3
|
+
|
|
4
|
+
// src/resolve-asset-source.ts
|
|
5
|
+
|
|
6
|
+
// src/deriveAssetName.ts
|
|
7
|
+
function baseName(p) {
|
|
8
|
+
const trimmed = p.replace(/[/\\]+$/, "");
|
|
9
|
+
const idx = Math.max(trimmed.lastIndexOf("/"), trimmed.lastIndexOf("\\"));
|
|
10
|
+
return idx === -1 ? trimmed : trimmed.slice(idx + 1);
|
|
11
|
+
}
|
|
12
|
+
function deriveAssetName(packagePath, assetCount, storedName) {
|
|
13
|
+
if (packagePath === null) {
|
|
14
|
+
return "";
|
|
15
|
+
}
|
|
16
|
+
{
|
|
17
|
+
return baseName(packagePath);
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
// src/errors.ts
|
|
22
|
+
var PackError = class extends Error {
|
|
23
|
+
code;
|
|
24
|
+
expected;
|
|
25
|
+
hint;
|
|
26
|
+
detail;
|
|
27
|
+
constructor(args) {
|
|
28
|
+
super(`[PackError ${args.code}] expected: ${args.expected}; hint: ${args.hint}`);
|
|
29
|
+
this.name = "PackError";
|
|
30
|
+
this.code = args.code;
|
|
31
|
+
this.expected = args.expected;
|
|
32
|
+
this.hint = args.hint;
|
|
33
|
+
this.detail = args.detail;
|
|
34
|
+
}
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
// src/resolve-asset-source.ts
|
|
38
|
+
function deriveSourceName(metaFileName) {
|
|
39
|
+
return metaFileName.replace(/\.meta\.json$/, "");
|
|
40
|
+
}
|
|
41
|
+
var PATH_REF_RE = /^@([^/]+)\/(.+)$/;
|
|
42
|
+
function isPathEscape(pathDir, resolved) {
|
|
43
|
+
const rel = posix.relative(pathDir, resolved);
|
|
44
|
+
return rel.startsWith("..") || posix.isAbsolute(rel);
|
|
45
|
+
}
|
|
46
|
+
function resolveAssetSource(metaPath, source, paths) {
|
|
47
|
+
if (source === void 0) {
|
|
48
|
+
const metaDir = dirname(metaPath);
|
|
49
|
+
const metaName = deriveAssetName(metaPath);
|
|
50
|
+
const derived = deriveSourceName(metaName);
|
|
51
|
+
return ok(resolve(metaDir, derived));
|
|
52
|
+
}
|
|
53
|
+
if (source.startsWith("@")) {
|
|
54
|
+
const match = source.match(PATH_REF_RE);
|
|
55
|
+
if (!match) {
|
|
56
|
+
return err(
|
|
57
|
+
new PackError({
|
|
58
|
+
code: "pack-malformed-path-ref",
|
|
59
|
+
expected: "source in format @<name>/<rest>",
|
|
60
|
+
hint: PACK_ERROR_HINTS["pack-malformed-path-ref"],
|
|
61
|
+
detail: {
|
|
62
|
+
code: "pack-malformed-path-ref",
|
|
63
|
+
reason: "format",
|
|
64
|
+
rawSource: source,
|
|
65
|
+
expectedFormat: "@<name>/<rest>"
|
|
66
|
+
}
|
|
67
|
+
})
|
|
68
|
+
);
|
|
69
|
+
}
|
|
70
|
+
const [, name, rest] = match;
|
|
71
|
+
const pathDir = paths[name];
|
|
72
|
+
if (pathDir === void 0) {
|
|
73
|
+
return err(
|
|
74
|
+
new PackError({
|
|
75
|
+
code: "pack-unknown-path",
|
|
76
|
+
expected: "path name found in package.json#forgeax.assets.paths",
|
|
77
|
+
hint: PACK_ERROR_HINTS["pack-unknown-path"],
|
|
78
|
+
detail: {
|
|
79
|
+
code: "pack-unknown-path",
|
|
80
|
+
pathName: name,
|
|
81
|
+
knownNames: Object.keys(paths)
|
|
82
|
+
}
|
|
83
|
+
})
|
|
84
|
+
);
|
|
85
|
+
}
|
|
86
|
+
const resolved = resolve(pathDir, rest);
|
|
87
|
+
if (isPathEscape(pathDir, resolved)) {
|
|
88
|
+
return err(
|
|
89
|
+
new PackError({
|
|
90
|
+
code: "pack-malformed-path-ref",
|
|
91
|
+
expected: "rest path must not escape the declared path directory",
|
|
92
|
+
hint: PACK_ERROR_HINTS["pack-malformed-path-ref"],
|
|
93
|
+
detail: {
|
|
94
|
+
code: "pack-malformed-path-ref",
|
|
95
|
+
reason: "escape",
|
|
96
|
+
rawSource: source,
|
|
97
|
+
expectedFormat: "@<name>/<rest>"
|
|
98
|
+
}
|
|
99
|
+
})
|
|
100
|
+
);
|
|
101
|
+
}
|
|
102
|
+
return ok(resolved);
|
|
103
|
+
}
|
|
104
|
+
return ok(resolve(dirname(metaPath), source));
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
export { resolveAssetSource };
|
|
108
|
+
//# sourceMappingURL=resolve-asset-source.mjs.map
|
|
109
|
+
//# sourceMappingURL=resolve-asset-source.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/deriveAssetName.ts","../src/errors.ts","../src/resolve-asset-source.ts"],"names":["resultOk","resultErr"],"mappings":";;;;;;AAOA,SAAS,SAAS,CAAA,EAAmB;AACnC,EAAA,MAAM,OAAA,GAAU,CAAA,CAAE,OAAA,CAAQ,SAAA,EAAW,EAAE,CAAA;AACvC,EAAA,MAAM,GAAA,GAAM,IAAA,CAAK,GAAA,CAAI,OAAA,CAAQ,WAAA,CAAY,GAAG,CAAA,EAAG,OAAA,CAAQ,WAAA,CAAY,IAAI,CAAC,CAAA;AACxE,EAAA,OAAO,QAAQ,EAAA,GAAK,OAAA,GAAU,OAAA,CAAQ,KAAA,CAAM,MAAM,CAAC,CAAA;AACrD;AAeO,SAAS,eAAA,CACd,WAAA,EACA,UAAA,EACA,UAAA,EACQ;AACR,EAAA,IAAI,gBAAgB,IAAA,EAAM;AACxB,IAAA,OAAqB,EAAA;AAAA,EACvB;AACA,EAAsB;AACpB,IAAA,OAAO,SAAS,WAAW,CAAA;AAAA,EAC7B;AAKF;;;ACdO,IAAM,SAAA,GAAN,cAAwB,KAAA,CAAM;AAAA,EAC1B,IAAA;AAAA,EACA,QAAA;AAAA,EACA,IAAA;AAAA,EACA,MAAA;AAAA,EAET,YAAY,IAAA,EAKT;AACD,IAAA,KAAA,CAAM,CAAA,WAAA,EAAc,KAAK,IAAI,CAAA,YAAA,EAAe,KAAK,QAAQ,CAAA,QAAA,EAAW,IAAA,CAAK,IAAI,CAAA,CAAE,CAAA;AAC/E,IAAA,IAAA,CAAK,IAAA,GAAO,WAAA;AACZ,IAAA,IAAA,CAAK,OAAO,IAAA,CAAK,IAAA;AACjB,IAAA,IAAA,CAAK,WAAW,IAAA,CAAK,QAAA;AACrB,IAAA,IAAA,CAAK,OAAO,IAAA,CAAK,IAAA;AACjB,IAAA,IAAA,CAAK,SAAS,IAAA,CAAK,MAAA;AAAA,EACrB;AACF,CAAA;;;ACxCA,SAAS,iBAAiB,YAAA,EAA8B;AACtD,EAAA,OAAO,YAAA,CAAa,OAAA,CAAQ,eAAA,EAAiB,EAAE,CAAA;AACjD;AAEA,IAAM,WAAA,GAAc,kBAAA;AAEpB,SAAS,YAAA,CAAa,SAAiB,QAAA,EAA2B;AAChE,EAAA,MAAM,GAAA,GAAM,KAAA,CAAM,QAAA,CAAS,OAAA,EAAS,QAAQ,CAAA;AAC5C,EAAA,OAAO,IAAI,UAAA,CAAW,IAAI,CAAA,IAAK,KAAA,CAAM,WAAW,GAAG,CAAA;AACrD;AAEO,SAAS,kBAAA,CACd,QAAA,EACA,MAAA,EACA,KAAA,EAC2B;AAC3B,EAAA,IAAI,WAAW,MAAA,EAAW;AACxB,IAAA,MAAM,OAAA,GAAU,QAAQ,QAAQ,CAAA;AAChC,IAAA,MAAM,QAAA,GAAW,eAAA,CAAgB,QAAW,CAAA;AAC5C,IAAA,MAAM,OAAA,GAAU,iBAAiB,QAAQ,CAAA;AACzC,IAAA,OAAOA,EAAA,CAAS,OAAA,CAAQ,OAAA,EAAS,OAAO,CAAC,CAAA;AAAA,EAC3C;AAEA,EAAA,IAAI,MAAA,CAAO,UAAA,CAAW,GAAG,CAAA,EAAG;AAC1B,IAAA,MAAM,KAAA,GAAQ,MAAA,CAAO,KAAA,CAAM,WAAW,CAAA;AACtC,IAAA,IAAI,CAAC,KAAA,EAAO;AACV,MAAA,OAAOC,GAAA;AAAA,QACL,IAAI,SAAA,CAAU;AAAA,UACZ,IAAA,EAAM,yBAAA;AAAA,UACN,QAAA,EAAU,iCAAA;AAAA,UACV,IAAA,EAAM,iBAAiB,yBAAyB,CAAA;AAAA,UAChD,MAAA,EAAQ;AAAA,YACN,IAAA,EAAM,yBAAA;AAAA,YACN,MAAA,EAAQ,QAAA;AAAA,YACR,SAAA,EAAW,MAAA;AAAA,YACX,cAAA,EAAgB;AAAA;AAClB,SACD;AAAA,OACH;AAAA,IACF;AAEA,IAAA,MAAM,GAAG,IAAA,EAAM,IAAI,CAAA,GAAI,KAAA;AACvB,IAAA,MAAM,OAAA,GAAU,MAAM,IAAI,CAAA;AAE1B,IAAA,IAAI,YAAY,MAAA,EAAW;AACzB,MAAA,OAAOA,GAAA;AAAA,QACL,IAAI,SAAA,CAAU;AAAA,UACZ,IAAA,EAAM,mBAAA;AAAA,UACN,QAAA,EAAU,sDAAA;AAAA,UACV,IAAA,EAAM,iBAAiB,mBAAmB,CAAA;AAAA,UAC1C,MAAA,EAAQ;AAAA,YACN,IAAA,EAAM,mBAAA;AAAA,YACN,QAAA,EAAU,IAAA;AAAA,YACV,UAAA,EAAY,MAAA,CAAO,IAAA,CAAK,KAAK;AAAA;AAC/B,SACD;AAAA,OACH;AAAA,IACF;AAEA,IAAA,MAAM,QAAA,GAAW,OAAA,CAAQ,OAAA,EAAS,IAAI,CAAA;AAEtC,IAAA,IAAI,YAAA,CAAa,OAAA,EAAS,QAAQ,CAAA,EAAG;AACnC,MAAA,OAAOA,GAAA;AAAA,QACL,IAAI,SAAA,CAAU;AAAA,UACZ,IAAA,EAAM,yBAAA;AAAA,UACN,QAAA,EAAU,uDAAA;AAAA,UACV,IAAA,EAAM,iBAAiB,yBAAyB,CAAA;AAAA,UAChD,MAAA,EAAQ;AAAA,YACN,IAAA,EAAM,yBAAA;AAAA,YACN,MAAA,EAAQ,QAAA;AAAA,YACR,SAAA,EAAW,MAAA;AAAA,YACX,cAAA,EAAgB;AAAA;AAClB,SACD;AAAA,OACH;AAAA,IACF;AAEA,IAAA,OAAOD,GAAS,QAAQ,CAAA;AAAA,EAC1B;AAEA,EAAA,OAAOA,GAAS,OAAA,CAAQ,OAAA,CAAQ,QAAQ,CAAA,EAAG,MAAM,CAAC,CAAA;AACpD","file":"resolve-asset-source.mjs","sourcesContent":["/**\n * Last path segment of a `/`- or `\\`-separated path, trailing separators\n * stripped. Inlined rather than imported from `node:path` so this module stays\n * browser-safe: the dev-server pack path (`vite-plugin-pack` `/__pack/`) runs\n * `buildCatalog` -> `deriveAssetName` in client code where `node:path` is\n * externalized and `path.basename` throws.\n */\nfunction baseName(p: string): string {\n const trimmed = p.replace(/[/\\\\]+$/, '');\n const idx = Math.max(trimmed.lastIndexOf('/'), trimmed.lastIndexOf('\\\\'));\n return idx === -1 ? trimmed : trimmed.slice(idx + 1);\n}\n\n/**\n * Derive an asset's display name from package metadata.\n *\n * Pure function -- zero IO, zero side effects, browser-safe. Build-time\n * (build-catalog) and runtime (resolveName) share this single source of truth\n * for the XOR name-resolution rules (plan-strategy D-6).\n *\n * Branches:\n * 1. single-asset package (assetCount === 1) -> baseName(packagePath)\n * 2. multi-asset package + storedName -> storedName\n * 3. multi-asset package + no storedName (AC-15.1) -> baseName(packagePath)\n * 4. null packagePath + no storedName (AC-15.2) -> ''\n */\nexport function deriveAssetName(\n packagePath: string | null,\n assetCount: number,\n storedName?: string,\n): string {\n if (packagePath === null) {\n return storedName ?? '';\n }\n if (assetCount === 1) {\n return baseName(packagePath);\n }\n if (storedName !== undefined) {\n return storedName;\n }\n return baseName(packagePath);\n}\n","// errors.ts — PackError class (feat-20260513-guid-asset-package-system w15)\n//\n// Four-field surface: .code / .expected / .hint / .detail\n// Structurally parallel to AssetError / RhiError / RemoteError\n// (charter proposition 5 consistent abstraction).\n//\n// .detail is narrowed per .code via PackErrorDetail discriminated union\n// (requirements §6.2 AC-07; plan-strategy §D-5).\n\nimport type { PackErrorCode, PackErrorDetail } from '@forgeax/engine-types';\n\n/**\n * Structured error for the engine-pack disk scanner fail-fast chain.\n *\n * AI users consume via exhaustive switch on .code — no default case needed:\n * ```ts\n * switch (err.code) {\n * case 'pack-guid-collision':\n * console.error(err.detail.paths);\n * break;\n * case 'pack-cyclic-reference':\n * console.error(err.detail.cycle);\n * break;\n * // ...all 8 cases\n * }\n * ```\n */\nexport class PackError extends Error {\n readonly code: PackErrorCode;\n readonly expected: string;\n readonly hint: string;\n readonly detail: PackErrorDetail;\n\n constructor(args: {\n code: PackErrorCode;\n expected: string;\n hint: string;\n detail: PackErrorDetail;\n }) {\n super(`[PackError ${args.code}] expected: ${args.expected}; hint: ${args.hint}`);\n this.name = 'PackError';\n this.code = args.code;\n this.expected = args.expected;\n this.hint = args.hint;\n this.detail = args.detail;\n }\n}\n","import { dirname, posix, resolve } from 'node:path';\nimport type { Result } from '@forgeax/engine-types';\nimport { PACK_ERROR_HINTS, err as resultErr, ok as resultOk } from '@forgeax/engine-types';\nimport { deriveAssetName } from './deriveAssetName.js';\nimport { PackError } from './errors.js';\n\nfunction deriveSourceName(metaFileName: string): string {\n return metaFileName.replace(/\\.meta\\.json$/, '');\n}\n\nconst PATH_REF_RE = /^@([^/]+)\\/(.+)$/;\n\nfunction isPathEscape(pathDir: string, resolved: string): boolean {\n const rel = posix.relative(pathDir, resolved);\n return rel.startsWith('..') || posix.isAbsolute(rel);\n}\n\nexport function resolveAssetSource(\n metaPath: string,\n source: string | undefined,\n paths: Record<string, string>,\n): Result<string, PackError> {\n if (source === undefined) {\n const metaDir = dirname(metaPath);\n const metaName = deriveAssetName(metaPath, 1);\n const derived = deriveSourceName(metaName);\n return resultOk(resolve(metaDir, derived));\n }\n\n if (source.startsWith('@')) {\n const match = source.match(PATH_REF_RE);\n if (!match) {\n return resultErr(\n new PackError({\n code: 'pack-malformed-path-ref',\n expected: 'source in format @<name>/<rest>',\n hint: PACK_ERROR_HINTS['pack-malformed-path-ref'],\n detail: {\n code: 'pack-malformed-path-ref',\n reason: 'format',\n rawSource: source,\n expectedFormat: '@<name>/<rest>',\n },\n }),\n );\n }\n\n const [, name, rest] = match as [string, string, string];\n const pathDir = paths[name];\n\n if (pathDir === undefined) {\n return resultErr(\n new PackError({\n code: 'pack-unknown-path',\n expected: 'path name found in package.json#forgeax.assets.paths',\n hint: PACK_ERROR_HINTS['pack-unknown-path'],\n detail: {\n code: 'pack-unknown-path',\n pathName: name,\n knownNames: Object.keys(paths),\n },\n }),\n );\n }\n\n const resolved = resolve(pathDir, rest);\n\n if (isPathEscape(pathDir, resolved)) {\n return resultErr(\n new PackError({\n code: 'pack-malformed-path-ref',\n expected: 'rest path must not escape the declared path directory',\n hint: PACK_ERROR_HINTS['pack-malformed-path-ref'],\n detail: {\n code: 'pack-malformed-path-ref',\n reason: 'escape',\n rawSource: source,\n expectedFormat: '@<name>/<rest>',\n },\n }),\n );\n }\n\n return resultOk(resolved);\n }\n\n return resultOk(resolve(dirname(metaPath), source));\n}\n"]}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { AssetPublicationTuple, AssetRuntimeArtifactDescriptor, PackV2, PackV2Error, Result } from '@forgeax/engine-types';
|
|
2
|
+
export interface RuntimeAssetProjectionInput<P = unknown> {
|
|
3
|
+
readonly guid: string;
|
|
4
|
+
readonly kind: string;
|
|
5
|
+
readonly payload: P;
|
|
6
|
+
readonly refs: readonly string[];
|
|
7
|
+
readonly artifacts: Readonly<Record<string, AssetRuntimeArtifactDescriptor>>;
|
|
8
|
+
}
|
|
9
|
+
export interface RuntimePackProjectionInput<P = unknown> extends AssetPublicationTuple {
|
|
10
|
+
readonly assets: readonly RuntimeAssetProjectionInput<P>[];
|
|
11
|
+
}
|
|
12
|
+
/** Project producer facts into the only runtime Pack v2 envelope. */
|
|
13
|
+
export declare function projectRuntimePack<P = unknown>(value: unknown): Result<PackV2<P>, PackV2Error>;
|
|
14
|
+
//# sourceMappingURL=runtime-projection.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runtime-projection.d.ts","sourceRoot":"","sources":["../src/runtime-projection.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAEV,qBAAqB,EACrB,8BAA8B,EAC9B,MAAM,EACN,WAAW,EACX,MAAM,EACP,MAAM,uBAAuB,CAAC;AAG/B,MAAM,WAAW,2BAA2B,CAAC,CAAC,GAAG,OAAO;IACtD,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC;IACpB,QAAQ,CAAC,IAAI,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,QAAQ,CAAC,SAAS,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,8BAA8B,CAAC,CAAC,CAAC;CAC9E;AAED,MAAM,WAAW,0BAA0B,CAAC,CAAC,GAAG,OAAO,CAAE,SAAQ,qBAAqB;IACpF,QAAQ,CAAC,MAAM,EAAE,SAAS,2BAA2B,CAAC,CAAC,CAAC,EAAE,CAAC;CAC5D;AA2CD,qEAAqE;AACrE,wBAAgB,kBAAkB,CAAC,CAAC,GAAG,OAAO,EAAE,KAAK,EAAE,OAAO,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,WAAW,CAAC,CAmC9F"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import type { AssetPublicationEnvelope, AssetPublicationExternalEvidence, AssetPublicationOutput } from '@forgeax/engine-types';
|
|
2
|
+
export interface RuntimePackAssetInput {
|
|
3
|
+
readonly guid: string;
|
|
4
|
+
readonly kind: string;
|
|
5
|
+
readonly name?: string;
|
|
6
|
+
readonly payload: unknown;
|
|
7
|
+
readonly refs?: readonly string[];
|
|
8
|
+
readonly artifacts?: Readonly<Record<string, unknown>>;
|
|
9
|
+
}
|
|
10
|
+
export interface RuntimePackInput {
|
|
11
|
+
readonly assets: readonly RuntimePackAssetInput[];
|
|
12
|
+
}
|
|
13
|
+
export interface RuntimePackEnvelope {
|
|
14
|
+
readonly schemaVersion: '2.0.0';
|
|
15
|
+
readonly kind: 'internal-text-package';
|
|
16
|
+
readonly scopeId: string;
|
|
17
|
+
readonly generation: number;
|
|
18
|
+
readonly digest: string;
|
|
19
|
+
readonly outputSetDigest: string;
|
|
20
|
+
readonly assets: readonly RuntimePackAsset[];
|
|
21
|
+
}
|
|
22
|
+
export interface RuntimePackPublication {
|
|
23
|
+
readonly pack: RuntimePackEnvelope;
|
|
24
|
+
readonly publication: AssetPublicationEnvelope;
|
|
25
|
+
}
|
|
26
|
+
interface RuntimePackAsset extends RuntimePackAssetInput {
|
|
27
|
+
readonly refs: readonly string[];
|
|
28
|
+
readonly artifacts: Readonly<Record<string, unknown>>;
|
|
29
|
+
}
|
|
30
|
+
export interface RuntimePackPublicationInput {
|
|
31
|
+
readonly pack: RuntimePackInput;
|
|
32
|
+
readonly scopeId: string;
|
|
33
|
+
readonly sourcePath: string;
|
|
34
|
+
readonly sourceRevision: string;
|
|
35
|
+
readonly packageUrl: string;
|
|
36
|
+
readonly inputFingerprint?: string;
|
|
37
|
+
readonly digest?: string;
|
|
38
|
+
readonly generation?: number;
|
|
39
|
+
readonly outputs?: readonly AssetPublicationOutput[];
|
|
40
|
+
readonly externalEvidence?: readonly AssetPublicationExternalEvidence[];
|
|
41
|
+
}
|
|
42
|
+
export declare function createRuntimePackPublication(input: RuntimePackPublicationInput): RuntimePackPublication;
|
|
43
|
+
export {};
|
|
44
|
+
//# sourceMappingURL=runtime-publication.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runtime-publication.d.ts","sourceRoot":"","sources":["../src/runtime-publication.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,wBAAwB,EACxB,gCAAgC,EAChC,sBAAsB,EACvB,MAAM,uBAAuB,CAAC;AAE/B,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;IAC1B,QAAQ,CAAC,IAAI,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAClC,QAAQ,CAAC,SAAS,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;CACxD;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,MAAM,EAAE,SAAS,qBAAqB,EAAE,CAAC;CACnD;AAED,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,aAAa,EAAE,OAAO,CAAC;IAChC,QAAQ,CAAC,IAAI,EAAE,uBAAuB,CAAC;IACvC,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC,QAAQ,CAAC,MAAM,EAAE,SAAS,gBAAgB,EAAE,CAAC;CAC9C;AAED,MAAM,WAAW,sBAAsB;IACrC,QAAQ,CAAC,IAAI,EAAE,mBAAmB,CAAC;IACnC,QAAQ,CAAC,WAAW,EAAE,wBAAwB,CAAC;CAChD;AAED,UAAU,gBAAiB,SAAQ,qBAAqB;IACtD,QAAQ,CAAC,IAAI,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,QAAQ,CAAC,SAAS,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC;CACvD;AAED,MAAM,WAAW,2BAA2B;IAC1C,QAAQ,CAAC,IAAI,EAAE,gBAAgB,CAAC;IAChC,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,cAAc,EAAE,MAAM,CAAC;IAChC,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,gBAAgB,CAAC,EAAE,MAAM,CAAC;IACnC,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,OAAO,CAAC,EAAE,SAAS,sBAAsB,EAAE,CAAC;IACrD,QAAQ,CAAC,gBAAgB,CAAC,EAAE,SAAS,gCAAgC,EAAE,CAAC;CACzE;AAoFD,wBAAgB,4BAA4B,CAC1C,KAAK,EAAE,2BAA2B,GACjC,sBAAsB,CAoDxB"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import type { PackV2, PackV2Error, Result } from '@forgeax/engine-types';
|
|
2
|
+
export { validateMeta, validatePack, validatePackV2 } from './schema-compiled.js';
|
|
3
|
+
/**
|
|
4
|
+
* Parse a Pack v2 envelope without loading the Node-only scanner/evidence
|
|
5
|
+
* barrel. Browser runtime consumers should import this subpath.
|
|
6
|
+
*/
|
|
7
|
+
export declare function parsePackV2(value: unknown): Result<PackV2, PackV2Error>;
|
|
8
|
+
//# sourceMappingURL=runtime.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../src/runtime.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,uBAAuB,CAAC;AAKzE,OAAO,EAAE,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAElF;;;GAGG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAAC,MAAM,EAAE,WAAW,CAAC,CAWvE"}
|