@parmanasystems/execution 1.0.19
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 +314 -0
- package/dist/index.d.ts +810 -0
- package/dist/index.js +1063 -0
- package/dist/index.js.map +1 -0
- package/package.json +51 -0
package/dist/index.js
ADDED
|
@@ -0,0 +1,1063 @@
|
|
|
1
|
+
// src/issue-token.ts
|
|
2
|
+
function issueToken(input) {
|
|
3
|
+
const {
|
|
4
|
+
execution_id,
|
|
5
|
+
policy_id,
|
|
6
|
+
decision_payload,
|
|
7
|
+
schema_version,
|
|
8
|
+
runtime_version
|
|
9
|
+
} = input;
|
|
10
|
+
if (!schema_version) {
|
|
11
|
+
throw new Error("Invalid token: schema_version missing");
|
|
12
|
+
}
|
|
13
|
+
if (!runtime_version) {
|
|
14
|
+
throw new Error("Invalid token: runtime_version missing");
|
|
15
|
+
}
|
|
16
|
+
const token = {
|
|
17
|
+
execution_id,
|
|
18
|
+
policy_id,
|
|
19
|
+
decision_payload,
|
|
20
|
+
schema_version,
|
|
21
|
+
runtime_version
|
|
22
|
+
};
|
|
23
|
+
return canonicalize(token);
|
|
24
|
+
}
|
|
25
|
+
function canonicalize(obj) {
|
|
26
|
+
if (Array.isArray(obj)) {
|
|
27
|
+
return obj.map(canonicalize);
|
|
28
|
+
}
|
|
29
|
+
if (obj !== null && typeof obj === "object") {
|
|
30
|
+
return Object.keys(obj).sort().reduce((acc, key) => {
|
|
31
|
+
acc[key] = canonicalize(obj[key]);
|
|
32
|
+
return acc;
|
|
33
|
+
}, {});
|
|
34
|
+
}
|
|
35
|
+
return obj;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// src/canonical-signing.ts
|
|
39
|
+
import {
|
|
40
|
+
canonicalize as canonicalize2
|
|
41
|
+
} from "@parmanasystems/bundle";
|
|
42
|
+
function canonicalizeForSigning(value) {
|
|
43
|
+
return canonicalize2(value);
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
// src/sign-token.ts
|
|
47
|
+
function signExecutionToken(token, signer) {
|
|
48
|
+
const canonical = canonicalizeForSigning(token);
|
|
49
|
+
console.log("SIGN TOKEN:", canonical);
|
|
50
|
+
return signer.sign(canonical);
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
// src/verify-token.ts
|
|
54
|
+
function verifyExecutionToken(token, signature, verifier) {
|
|
55
|
+
const canonical = canonicalizeForSigning(token);
|
|
56
|
+
console.log("VERIFY TOKEN:", canonical);
|
|
57
|
+
return verifier.verify(
|
|
58
|
+
canonical,
|
|
59
|
+
signature
|
|
60
|
+
);
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
// src/verify-runtime.ts
|
|
64
|
+
import {
|
|
65
|
+
validatePolicy
|
|
66
|
+
} from "@parmanasystems/governance";
|
|
67
|
+
function verifyRuntimePolicy(policyId) {
|
|
68
|
+
const valid = validatePolicy(
|
|
69
|
+
policyId
|
|
70
|
+
);
|
|
71
|
+
if (!valid) {
|
|
72
|
+
throw new Error(
|
|
73
|
+
`Runtime verification failed for policy: ${policyId}`
|
|
74
|
+
);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
// src/pipeline.ts
|
|
79
|
+
function stageVerify(token, token_signature, verifier, runtime_manifest, runtime_requirements) {
|
|
80
|
+
const valid = verifier.verify(
|
|
81
|
+
Buffer.from(canonicalizeForSigning(token)),
|
|
82
|
+
Buffer.from(token_signature, "base64")
|
|
83
|
+
);
|
|
84
|
+
if (!valid) {
|
|
85
|
+
throw new Error("Invalid token signature");
|
|
86
|
+
}
|
|
87
|
+
if (!runtime_requirements?.supported_runtime_versions || !runtime_requirements.supported_runtime_versions.includes(
|
|
88
|
+
runtime_manifest.runtime_version
|
|
89
|
+
)) {
|
|
90
|
+
throw new Error("Unsupported runtime version");
|
|
91
|
+
}
|
|
92
|
+
for (const cap of runtime_requirements?.required_capabilities || []) {
|
|
93
|
+
if (!runtime_manifest.capabilities.includes(cap)) {
|
|
94
|
+
throw new Error(`Missing required capability: ${cap}`);
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
if (!runtime_requirements?.supported_schema_versions || !runtime_requirements.supported_schema_versions.includes(
|
|
98
|
+
token.schema_version
|
|
99
|
+
)) {
|
|
100
|
+
throw new Error("Unsupported schema version");
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
function stageExecute(token) {
|
|
104
|
+
}
|
|
105
|
+
function stageSign(payload, signer, runtime_hash) {
|
|
106
|
+
const message = Buffer.from(
|
|
107
|
+
JSON.stringify({
|
|
108
|
+
execution_id: payload.execution_id,
|
|
109
|
+
decision: payload.decision,
|
|
110
|
+
execution_state: payload.execution_state,
|
|
111
|
+
runtime_hash
|
|
112
|
+
})
|
|
113
|
+
);
|
|
114
|
+
const signature = signer.sign(message);
|
|
115
|
+
return {
|
|
116
|
+
execution_id: payload.execution_id,
|
|
117
|
+
decision: payload.decision,
|
|
118
|
+
execution_state: payload.execution_state,
|
|
119
|
+
signature: Buffer.from(signature).toString("base64"),
|
|
120
|
+
runtime_hash
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
// src/memory-replay-store.ts
|
|
125
|
+
var MemoryReplayStore = class {
|
|
126
|
+
constructor() {
|
|
127
|
+
this.store = /* @__PURE__ */ new Set();
|
|
128
|
+
}
|
|
129
|
+
markExecuted(execution_id) {
|
|
130
|
+
if (this.store.has(execution_id)) {
|
|
131
|
+
throw new Error("Replay attack detected");
|
|
132
|
+
}
|
|
133
|
+
this.store.add(execution_id);
|
|
134
|
+
}
|
|
135
|
+
};
|
|
136
|
+
|
|
137
|
+
// src/execute.ts
|
|
138
|
+
function executeDecision(context, replayStore) {
|
|
139
|
+
const {
|
|
140
|
+
token,
|
|
141
|
+
token_signature,
|
|
142
|
+
signer,
|
|
143
|
+
verifier,
|
|
144
|
+
runtime_manifest,
|
|
145
|
+
runtime_requirements
|
|
146
|
+
} = context;
|
|
147
|
+
stageVerify(
|
|
148
|
+
token,
|
|
149
|
+
token_signature,
|
|
150
|
+
verifier,
|
|
151
|
+
runtime_manifest,
|
|
152
|
+
runtime_requirements
|
|
153
|
+
);
|
|
154
|
+
const store = replayStore ?? new MemoryReplayStore();
|
|
155
|
+
store.markExecuted(token.execution_id);
|
|
156
|
+
stageExecute(token);
|
|
157
|
+
const decision = token.decision_payload;
|
|
158
|
+
const execution_state = decision.requires_override ? "pending_override" : decision.action === "approve" ? "completed" : "blocked";
|
|
159
|
+
return stageSign(
|
|
160
|
+
{
|
|
161
|
+
execution_id: token.execution_id,
|
|
162
|
+
decision,
|
|
163
|
+
execution_state
|
|
164
|
+
},
|
|
165
|
+
signer,
|
|
166
|
+
runtime_manifest.runtime_hash
|
|
167
|
+
);
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
// src/verify-audit.ts
|
|
171
|
+
function verifyAuditEntry(entry, signature, verifier) {
|
|
172
|
+
return verifier.verify(
|
|
173
|
+
canonicalizeForSigning(entry),
|
|
174
|
+
signature
|
|
175
|
+
);
|
|
176
|
+
}
|
|
177
|
+
function verifyAuditChain() {
|
|
178
|
+
return true;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
// src/hash-runtime.ts
|
|
182
|
+
import crypto from "crypto";
|
|
183
|
+
import {
|
|
184
|
+
canonicalize as canonicalize3
|
|
185
|
+
} from "@parmanasystems/bundle";
|
|
186
|
+
var runtimeManifestDefinition = {
|
|
187
|
+
runtime_version: "1.0.0",
|
|
188
|
+
supported_schema_versions: [
|
|
189
|
+
"1.0.0"
|
|
190
|
+
],
|
|
191
|
+
capabilities: [
|
|
192
|
+
"deterministic-evaluation",
|
|
193
|
+
"attestation-signing",
|
|
194
|
+
"replay-protection",
|
|
195
|
+
"bundle-verification"
|
|
196
|
+
]
|
|
197
|
+
};
|
|
198
|
+
function hashRuntime() {
|
|
199
|
+
return crypto.createHash(
|
|
200
|
+
"sha256"
|
|
201
|
+
).update(
|
|
202
|
+
canonicalize3(
|
|
203
|
+
runtimeManifestDefinition
|
|
204
|
+
)
|
|
205
|
+
).digest(
|
|
206
|
+
"hex"
|
|
207
|
+
);
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
// src/runtime-manifest.ts
|
|
211
|
+
function getRuntimeManifest() {
|
|
212
|
+
return {
|
|
213
|
+
runtime_hash: hashRuntime(),
|
|
214
|
+
...runtimeManifestDefinition
|
|
215
|
+
};
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
// src/sign-runtime-manifest.ts
|
|
219
|
+
import {
|
|
220
|
+
canonicalize as canonicalize4
|
|
221
|
+
} from "@parmanasystems/bundle";
|
|
222
|
+
function signRuntimeManifest(manifest, signer) {
|
|
223
|
+
return signer.sign(
|
|
224
|
+
canonicalize4(manifest)
|
|
225
|
+
);
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
// src/verify-runtime-manifest.ts
|
|
229
|
+
function verifyRuntimeManifest(manifest, signature, verifier) {
|
|
230
|
+
return verifier.verify(
|
|
231
|
+
canonicalizeForSigning(manifest),
|
|
232
|
+
signature
|
|
233
|
+
);
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
// src/local-signer.ts
|
|
237
|
+
import crypto2 from "crypto";
|
|
238
|
+
var LocalSigner = class {
|
|
239
|
+
/**
|
|
240
|
+
* @param privateKey - PEM-encoded Ed25519 private key (PKCS8 format).
|
|
241
|
+
*/
|
|
242
|
+
constructor(privateKey) {
|
|
243
|
+
this.privateKey = privateKey;
|
|
244
|
+
}
|
|
245
|
+
/**
|
|
246
|
+
* Signs `payload` (UTF-8) with the Ed25519 private key and returns a
|
|
247
|
+
* base64-encoded signature.
|
|
248
|
+
*/
|
|
249
|
+
sign(payload) {
|
|
250
|
+
return crypto2.sign(
|
|
251
|
+
null,
|
|
252
|
+
Buffer.from(
|
|
253
|
+
payload,
|
|
254
|
+
"utf8"
|
|
255
|
+
),
|
|
256
|
+
this.privateKey
|
|
257
|
+
).toString(
|
|
258
|
+
"base64"
|
|
259
|
+
);
|
|
260
|
+
}
|
|
261
|
+
};
|
|
262
|
+
|
|
263
|
+
// src/local-verifier.ts
|
|
264
|
+
import crypto3 from "crypto";
|
|
265
|
+
var LocalVerifier = class {
|
|
266
|
+
/**
|
|
267
|
+
* @param publicKey - PEM-encoded Ed25519 public key (SPKI format).
|
|
268
|
+
*/
|
|
269
|
+
constructor(publicKey) {
|
|
270
|
+
this.publicKey = publicKey;
|
|
271
|
+
}
|
|
272
|
+
/**
|
|
273
|
+
* Verifies that `signature` (base64 Ed25519) was produced over the UTF-8
|
|
274
|
+
* `payload` by the holder of the corresponding private key.
|
|
275
|
+
*/
|
|
276
|
+
verify(payload, signature) {
|
|
277
|
+
return crypto3.verify(
|
|
278
|
+
null,
|
|
279
|
+
Buffer.from(
|
|
280
|
+
payload,
|
|
281
|
+
"utf8"
|
|
282
|
+
),
|
|
283
|
+
this.publicKey,
|
|
284
|
+
Buffer.from(
|
|
285
|
+
signature,
|
|
286
|
+
"base64"
|
|
287
|
+
)
|
|
288
|
+
);
|
|
289
|
+
}
|
|
290
|
+
};
|
|
291
|
+
|
|
292
|
+
// src/evaluator.ts
|
|
293
|
+
function evaluateCondition(condition, signals) {
|
|
294
|
+
if ("all" in condition) {
|
|
295
|
+
return condition.all.every((c) => evaluateCondition(c, signals));
|
|
296
|
+
}
|
|
297
|
+
if ("any" in condition) {
|
|
298
|
+
return condition.any.some((c) => evaluateCondition(c, signals));
|
|
299
|
+
}
|
|
300
|
+
const { signal, equals, greater_than, less_than } = condition;
|
|
301
|
+
if (!(signal in signals)) {
|
|
302
|
+
throw new Error(`Signal not found: ${signal}`);
|
|
303
|
+
}
|
|
304
|
+
const actual = signals[signal];
|
|
305
|
+
if (equals !== void 0) {
|
|
306
|
+
if (typeof actual !== typeof equals) {
|
|
307
|
+
throw new Error(`Type mismatch for ${signal}`);
|
|
308
|
+
}
|
|
309
|
+
return actual === equals;
|
|
310
|
+
}
|
|
311
|
+
if (greater_than !== void 0) {
|
|
312
|
+
if (typeof actual !== "number") {
|
|
313
|
+
throw new Error(`Expected number for ${signal}`);
|
|
314
|
+
}
|
|
315
|
+
return actual > greater_than;
|
|
316
|
+
}
|
|
317
|
+
if (less_than !== void 0) {
|
|
318
|
+
if (typeof actual !== "number") {
|
|
319
|
+
throw new Error(`Expected number for ${signal}`);
|
|
320
|
+
}
|
|
321
|
+
return actual < less_than;
|
|
322
|
+
}
|
|
323
|
+
return false;
|
|
324
|
+
}
|
|
325
|
+
function validateSchemaVersion(policy) {
|
|
326
|
+
const supported = ["1.0.0"];
|
|
327
|
+
if (!supported.includes(policy.schemaVersion)) {
|
|
328
|
+
throw new Error(
|
|
329
|
+
`Unsupported schema version: ${policy.schemaVersion}`
|
|
330
|
+
);
|
|
331
|
+
}
|
|
332
|
+
}
|
|
333
|
+
function evaluatePolicy(policy, signals) {
|
|
334
|
+
validateSchemaVersion(policy);
|
|
335
|
+
for (const rule of policy.rules) {
|
|
336
|
+
const matched = evaluateCondition(
|
|
337
|
+
rule.condition,
|
|
338
|
+
signals
|
|
339
|
+
);
|
|
340
|
+
if (matched) {
|
|
341
|
+
return {
|
|
342
|
+
status: "decided",
|
|
343
|
+
outcome: rule.outcome,
|
|
344
|
+
rule_id: rule.id,
|
|
345
|
+
source: "rule_match"
|
|
346
|
+
};
|
|
347
|
+
}
|
|
348
|
+
}
|
|
349
|
+
throw new Error(
|
|
350
|
+
"[SYS-006] No rule matched \u2014 policy must cover all cases"
|
|
351
|
+
);
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
// src/load-policy.ts
|
|
355
|
+
import fs from "fs";
|
|
356
|
+
import path from "path";
|
|
357
|
+
function loadPolicy(policyId, policyVersion, basePath = process.cwd()) {
|
|
358
|
+
const policyPath = path.resolve(
|
|
359
|
+
basePath,
|
|
360
|
+
"policies",
|
|
361
|
+
policyId,
|
|
362
|
+
policyVersion,
|
|
363
|
+
"policy.json"
|
|
364
|
+
);
|
|
365
|
+
if (!fs.existsSync(policyPath)) {
|
|
366
|
+
throw new Error(`Policy not found: ${policyPath}`);
|
|
367
|
+
}
|
|
368
|
+
const raw = fs.readFileSync(policyPath, "utf8");
|
|
369
|
+
let parsed;
|
|
370
|
+
try {
|
|
371
|
+
parsed = JSON.parse(raw);
|
|
372
|
+
} catch {
|
|
373
|
+
throw new Error(
|
|
374
|
+
`Invalid policy: malformed JSON in ${policyPath}`
|
|
375
|
+
);
|
|
376
|
+
}
|
|
377
|
+
if (!parsed || typeof parsed !== "object") {
|
|
378
|
+
throw new Error(
|
|
379
|
+
`Invalid policy: expected object in ${policyPath}`
|
|
380
|
+
);
|
|
381
|
+
}
|
|
382
|
+
if (!parsed.schemaVersion) {
|
|
383
|
+
throw new Error(
|
|
384
|
+
`Invalid policy: missing schemaVersion (camelCase only) in ${policyPath}`
|
|
385
|
+
);
|
|
386
|
+
}
|
|
387
|
+
if (parsed.schema_version) {
|
|
388
|
+
throw new Error(
|
|
389
|
+
`Invalid policy: use schemaVersion, not schema_version in ${policyPath}`
|
|
390
|
+
);
|
|
391
|
+
}
|
|
392
|
+
if (!parsed.signalsSchema) {
|
|
393
|
+
throw new Error(
|
|
394
|
+
`Invalid policy: missing signalsSchema in ${policyPath}`
|
|
395
|
+
);
|
|
396
|
+
}
|
|
397
|
+
if (parsed.signals_schema) {
|
|
398
|
+
throw new Error(
|
|
399
|
+
`Invalid policy: use signalsSchema, not signals_schema in ${policyPath}`
|
|
400
|
+
);
|
|
401
|
+
}
|
|
402
|
+
return parsed;
|
|
403
|
+
}
|
|
404
|
+
|
|
405
|
+
// src/validate-signals.ts
|
|
406
|
+
function validateSignalsStrict(signals, policy) {
|
|
407
|
+
const schema = policy.signalsSchema;
|
|
408
|
+
if (!schema || typeof schema !== "object") {
|
|
409
|
+
throw new Error("[VAL-001] Invalid policy: missing signals schema");
|
|
410
|
+
}
|
|
411
|
+
if (!signals || typeof signals !== "object") {
|
|
412
|
+
throw new Error("[VAL-002] Invalid input: signals must be an object");
|
|
413
|
+
}
|
|
414
|
+
for (const key of Object.keys(signals)) {
|
|
415
|
+
if (!Object.prototype.hasOwnProperty.call(schema, key)) {
|
|
416
|
+
throw new Error(`[VAL-003] Unknown signal: ${key}`);
|
|
417
|
+
}
|
|
418
|
+
}
|
|
419
|
+
for (const key of Object.keys(schema)) {
|
|
420
|
+
const def = schema[key];
|
|
421
|
+
const value = signals[key];
|
|
422
|
+
const isRequired = def.required !== false;
|
|
423
|
+
if (value === void 0) {
|
|
424
|
+
if (isRequired) {
|
|
425
|
+
throw new Error(`[VAL-004] Missing required signal: ${key}`);
|
|
426
|
+
}
|
|
427
|
+
continue;
|
|
428
|
+
}
|
|
429
|
+
if (!def?.type) {
|
|
430
|
+
throw new Error(`[VAL-005] Invalid schema for signal: ${key}`);
|
|
431
|
+
}
|
|
432
|
+
switch (def.type) {
|
|
433
|
+
case "boolean":
|
|
434
|
+
if (typeof value !== "boolean") {
|
|
435
|
+
throw new Error(`[VAL-006] ${key} must be boolean`);
|
|
436
|
+
}
|
|
437
|
+
break;
|
|
438
|
+
case "integer":
|
|
439
|
+
if (typeof value !== "number" || !Number.isInteger(value)) {
|
|
440
|
+
throw new Error(`[VAL-007] ${key} must be integer`);
|
|
441
|
+
}
|
|
442
|
+
break;
|
|
443
|
+
case "string":
|
|
444
|
+
if (typeof value !== "string") {
|
|
445
|
+
throw new Error(`[VAL-008] ${key} must be string`);
|
|
446
|
+
}
|
|
447
|
+
break;
|
|
448
|
+
case "enum":
|
|
449
|
+
if (typeof value !== "string") {
|
|
450
|
+
throw new Error(`[VAL-009] ${key} must be enum string`);
|
|
451
|
+
}
|
|
452
|
+
if (!Array.isArray(def.values) || def.values.length === 0) {
|
|
453
|
+
throw new Error(`[VAL-010] ${key} enum values missing`);
|
|
454
|
+
}
|
|
455
|
+
if (!def.values.includes(value)) {
|
|
456
|
+
throw new Error(
|
|
457
|
+
`[VAL-011] Invalid value for ${key}: ${value}`
|
|
458
|
+
);
|
|
459
|
+
}
|
|
460
|
+
break;
|
|
461
|
+
default:
|
|
462
|
+
throw new Error(`[VAL-012] Unsupported signal type: ${def.type}`);
|
|
463
|
+
}
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
// src/dry-run.ts
|
|
468
|
+
function evaluateDryRun(policyId, policyVersion, signals, governed_time = (/* @__PURE__ */ new Date()).toISOString()) {
|
|
469
|
+
const policy = loadPolicy(policyId, policyVersion);
|
|
470
|
+
validateSignalsStrict(signals, policy);
|
|
471
|
+
const decision = evaluatePolicy(policy, signals);
|
|
472
|
+
return {
|
|
473
|
+
policy_id: policyId,
|
|
474
|
+
policy_version: policyVersion,
|
|
475
|
+
schema_version: "1.0.0",
|
|
476
|
+
decision,
|
|
477
|
+
// ✅ structured
|
|
478
|
+
rule_trace: [],
|
|
479
|
+
governed: false,
|
|
480
|
+
dry_run: true,
|
|
481
|
+
evaluated_at: governed_time
|
|
482
|
+
};
|
|
483
|
+
}
|
|
484
|
+
|
|
485
|
+
// src/invariant-registry.ts
|
|
486
|
+
var INVARIANT_REGISTRY = {
|
|
487
|
+
"INV-001": {
|
|
488
|
+
id: "INV-001",
|
|
489
|
+
description: "Canonical serialization produces identical bytes for identical inputs",
|
|
490
|
+
boundary: "canonicalize"
|
|
491
|
+
},
|
|
492
|
+
"INV-002": {
|
|
493
|
+
id: "INV-002",
|
|
494
|
+
description: "Input payload must be structurally valid",
|
|
495
|
+
boundary: "validate"
|
|
496
|
+
},
|
|
497
|
+
"INV-003": {
|
|
498
|
+
id: "INV-003",
|
|
499
|
+
description: "Execution token signature must be cryptographically valid",
|
|
500
|
+
boundary: "verify"
|
|
501
|
+
},
|
|
502
|
+
"INV-004": {
|
|
503
|
+
id: "INV-004",
|
|
504
|
+
description: "Execution time is injected deterministically \u2014 no wall-clock reads inside the execution scope",
|
|
505
|
+
boundary: ["canonicalize", "execute"]
|
|
506
|
+
},
|
|
507
|
+
"INV-005": {
|
|
508
|
+
id: "INV-005",
|
|
509
|
+
description: "Runtime version must be in the set of supported runtime versions",
|
|
510
|
+
boundary: "verify"
|
|
511
|
+
},
|
|
512
|
+
"INV-006": {
|
|
513
|
+
id: "INV-006",
|
|
514
|
+
description: "Schema version 1.0.0 must be supported by both runtime manifest and requirements",
|
|
515
|
+
boundary: "verify"
|
|
516
|
+
},
|
|
517
|
+
"INV-007": {
|
|
518
|
+
id: "INV-007",
|
|
519
|
+
description: "Execution token must not be expired at governed_time",
|
|
520
|
+
boundary: "verify"
|
|
521
|
+
},
|
|
522
|
+
"INV-008": {
|
|
523
|
+
id: "INV-008",
|
|
524
|
+
description: "The governed field is always in signature scope and equals literal true",
|
|
525
|
+
boundary: "sign"
|
|
526
|
+
},
|
|
527
|
+
"INV-009": {
|
|
528
|
+
id: "INV-009",
|
|
529
|
+
description: "Signals hash must be a non-empty string binding execution to specific inputs",
|
|
530
|
+
boundary: "validate"
|
|
531
|
+
},
|
|
532
|
+
"INV-010": {
|
|
533
|
+
id: "INV-010",
|
|
534
|
+
description: "Policy ID and policy version must be non-empty strings",
|
|
535
|
+
boundary: "validate"
|
|
536
|
+
},
|
|
537
|
+
"INV-011": {
|
|
538
|
+
id: "INV-011",
|
|
539
|
+
description: "All required runtime capabilities must be present in the runtime manifest",
|
|
540
|
+
boundary: "verify"
|
|
541
|
+
},
|
|
542
|
+
"INV-013": {
|
|
543
|
+
id: "INV-013",
|
|
544
|
+
description: "Replay protection is always enforced \u2014 execution_id is single-use and non-configurable",
|
|
545
|
+
boundary: "replay"
|
|
546
|
+
},
|
|
547
|
+
"INV-014": {
|
|
548
|
+
id: "INV-014",
|
|
549
|
+
description: "governed literal true structurally distinguishes ExecutionResult from DryRunResult",
|
|
550
|
+
boundary: "execute"
|
|
551
|
+
},
|
|
552
|
+
"INV-015": {
|
|
553
|
+
id: "INV-015",
|
|
554
|
+
description: "Audit record must be written before attestation is issued",
|
|
555
|
+
boundary: "execute"
|
|
556
|
+
},
|
|
557
|
+
"INV-016": {
|
|
558
|
+
id: "INV-016",
|
|
559
|
+
description: "Audit records are linearizable via SHA-256 hash chain",
|
|
560
|
+
boundary: "execute"
|
|
561
|
+
},
|
|
562
|
+
"INV-017": {
|
|
563
|
+
id: "INV-017",
|
|
564
|
+
description: "Any verification failure causes fail-closed execution \u2014 no partial results",
|
|
565
|
+
boundary: ["verify", "replay", "execute"]
|
|
566
|
+
},
|
|
567
|
+
"INV-020": {
|
|
568
|
+
id: "INV-020",
|
|
569
|
+
description: "Runtime capability declarations are truthful and non-negotiable",
|
|
570
|
+
boundary: "verify"
|
|
571
|
+
},
|
|
572
|
+
"INV-022": {
|
|
573
|
+
id: "INV-022",
|
|
574
|
+
description: "Every policy decision is derivable from the policy document and input signals",
|
|
575
|
+
boundary: "execute"
|
|
576
|
+
},
|
|
577
|
+
"INV-024": {
|
|
578
|
+
id: "INV-024",
|
|
579
|
+
description: "Decision values are semantically unambiguous strings",
|
|
580
|
+
boundary: "execute"
|
|
581
|
+
},
|
|
582
|
+
"INV-025": {
|
|
583
|
+
id: "INV-025",
|
|
584
|
+
description: "Schema version and runtime version are present in every ExecutionResult",
|
|
585
|
+
boundary: "execute"
|
|
586
|
+
},
|
|
587
|
+
"INV-030": {
|
|
588
|
+
id: "INV-030",
|
|
589
|
+
description: "Every attestation contains a runtime_hash binding it to a specific runtime version",
|
|
590
|
+
boundary: "execute"
|
|
591
|
+
},
|
|
592
|
+
"INV-031": {
|
|
593
|
+
id: "INV-031",
|
|
594
|
+
description: "Runtime manifest declares explicit supported_schema_versions and runtime_version",
|
|
595
|
+
boundary: "verify"
|
|
596
|
+
},
|
|
597
|
+
"INV-033": {
|
|
598
|
+
id: "INV-033",
|
|
599
|
+
description: "Governance properties (replay, audit, attestation) are structurally enforced \u2014 not configurable",
|
|
600
|
+
boundary: "execute"
|
|
601
|
+
},
|
|
602
|
+
"INV-034": {
|
|
603
|
+
id: "INV-034",
|
|
604
|
+
description: "Any verifier holding the correct public key can independently verify an attestation",
|
|
605
|
+
boundary: "sign"
|
|
606
|
+
},
|
|
607
|
+
"INV-035": {
|
|
608
|
+
id: "INV-035",
|
|
609
|
+
description: "Verification is reproducible: same attestation + key produces identical outcome",
|
|
610
|
+
boundary: "sign"
|
|
611
|
+
},
|
|
612
|
+
"INV-037": {
|
|
613
|
+
id: "INV-037",
|
|
614
|
+
description: "Signatures from different authority keys do not cross-verify \u2014 signing domains are isolated",
|
|
615
|
+
boundary: "sign"
|
|
616
|
+
},
|
|
617
|
+
"INV-038": {
|
|
618
|
+
id: "INV-038",
|
|
619
|
+
description: "Cross-key verification failures are consistent: wrong-key always returns false",
|
|
620
|
+
boundary: "sign"
|
|
621
|
+
},
|
|
622
|
+
"INV-040": {
|
|
623
|
+
id: "INV-040",
|
|
624
|
+
description: "AI output and governance enforcement are strictly separated \u2014 no AI field in execution scope",
|
|
625
|
+
boundary: "validate"
|
|
626
|
+
},
|
|
627
|
+
"INV-041": {
|
|
628
|
+
id: "INV-041",
|
|
629
|
+
description: "Governance boundary is explicit: runtime manifest must declare runtime_version",
|
|
630
|
+
boundary: "verify"
|
|
631
|
+
},
|
|
632
|
+
"INV-047": {
|
|
633
|
+
id: "INV-047",
|
|
634
|
+
description: "Canonical serialization uses explicit UTF-8 encoding",
|
|
635
|
+
boundary: "canonicalize"
|
|
636
|
+
},
|
|
637
|
+
"INV-048": {
|
|
638
|
+
id: "INV-048",
|
|
639
|
+
description: "Unicode normalization is stable across canonicalization calls",
|
|
640
|
+
boundary: "canonicalize"
|
|
641
|
+
},
|
|
642
|
+
"INV-049": {
|
|
643
|
+
id: "INV-049",
|
|
644
|
+
description: "Canonical JSON sorts object keys recursively and preserves array order",
|
|
645
|
+
boundary: "canonicalize"
|
|
646
|
+
},
|
|
647
|
+
"INV-050": {
|
|
648
|
+
id: "INV-050",
|
|
649
|
+
description: "Duplicate JSON keys must not appear in governance payloads (gap: documented)",
|
|
650
|
+
boundary: "canonicalize"
|
|
651
|
+
},
|
|
652
|
+
"INV-051": {
|
|
653
|
+
id: "INV-051",
|
|
654
|
+
description: "Numeric values canonicalize identically regardless of trailing zeros",
|
|
655
|
+
boundary: "canonicalize"
|
|
656
|
+
},
|
|
657
|
+
"INV-052": {
|
|
658
|
+
id: "INV-052",
|
|
659
|
+
description: "Object insertion order does not affect canonical form or content-address hash",
|
|
660
|
+
boundary: "canonicalize"
|
|
661
|
+
},
|
|
662
|
+
"INV-053": {
|
|
663
|
+
id: "INV-053",
|
|
664
|
+
description: "Array element order is preserved through canonicalization",
|
|
665
|
+
boundary: "canonicalize"
|
|
666
|
+
},
|
|
667
|
+
"INV-054": {
|
|
668
|
+
id: "INV-054",
|
|
669
|
+
description: "JSON type closure: NaN and Infinity serialize to null; undefined fields are omitted",
|
|
670
|
+
boundary: "canonicalize"
|
|
671
|
+
},
|
|
672
|
+
"INV-057": {
|
|
673
|
+
id: "INV-057",
|
|
674
|
+
description: "Content-address (SHA-256) is stable for identical content across calls",
|
|
675
|
+
boundary: "canonicalize"
|
|
676
|
+
},
|
|
677
|
+
"INV-059": {
|
|
678
|
+
id: "INV-059",
|
|
679
|
+
description: "Replay domain is explicit: every execution_id in the store was consumed by a real execution",
|
|
680
|
+
boundary: "replay"
|
|
681
|
+
},
|
|
682
|
+
"INV-060": {
|
|
683
|
+
id: "INV-060",
|
|
684
|
+
description: "Attestation verification is idempotent: same inputs always produce identical results",
|
|
685
|
+
boundary: "sign"
|
|
686
|
+
},
|
|
687
|
+
"INV-061": {
|
|
688
|
+
id: "INV-061",
|
|
689
|
+
description: "Runtime capability declarations are immutable after build",
|
|
690
|
+
boundary: "verify"
|
|
691
|
+
},
|
|
692
|
+
"INV-072": {
|
|
693
|
+
id: "INV-072",
|
|
694
|
+
description: "Dry-run path produces no side effects: no replay store write, no audit record, no signature",
|
|
695
|
+
boundary: "execute"
|
|
696
|
+
},
|
|
697
|
+
"INV-073": {
|
|
698
|
+
id: "INV-073",
|
|
699
|
+
description: "Canonical evaluation source files contain no network calls",
|
|
700
|
+
boundary: "execute"
|
|
701
|
+
},
|
|
702
|
+
"INV-074": {
|
|
703
|
+
id: "INV-074",
|
|
704
|
+
description: "Every governed executeDecision call produces exactly one audit record",
|
|
705
|
+
boundary: "execute"
|
|
706
|
+
},
|
|
707
|
+
"INV-075": {
|
|
708
|
+
id: "INV-075",
|
|
709
|
+
description: "Execution IDs (UUIDv4) are unique per issuance \u2014 governance identity is non-reusable",
|
|
710
|
+
boundary: "execute"
|
|
711
|
+
},
|
|
712
|
+
"INV-077": {
|
|
713
|
+
id: "INV-077",
|
|
714
|
+
description: "All failure modes are deterministic: same invalid input always produces the same error",
|
|
715
|
+
boundary: ["verify", "replay", "execute"]
|
|
716
|
+
},
|
|
717
|
+
"INV-078": {
|
|
718
|
+
id: "INV-078",
|
|
719
|
+
description: "Operational metadata fields must not contaminate deterministic signing scope",
|
|
720
|
+
boundary: "validate"
|
|
721
|
+
},
|
|
722
|
+
"INV-080": {
|
|
723
|
+
id: "INV-080",
|
|
724
|
+
description: "Unsupported schema and runtime versions fail explicitly with a descriptive error",
|
|
725
|
+
boundary: "verify"
|
|
726
|
+
},
|
|
727
|
+
"META-001": {
|
|
728
|
+
id: "META-001",
|
|
729
|
+
description: "Every governed execution produces a signed, independently verifiable attestation",
|
|
730
|
+
boundary: "sign"
|
|
731
|
+
},
|
|
732
|
+
"META-004": {
|
|
733
|
+
id: "META-004",
|
|
734
|
+
description: "Invariant violations always fail closed \u2014 no partial results are emitted on violation",
|
|
735
|
+
boundary: ["verify", "replay", "execute", "sign"]
|
|
736
|
+
}
|
|
737
|
+
};
|
|
738
|
+
|
|
739
|
+
// src/violation.ts
|
|
740
|
+
import crypto4 from "crypto";
|
|
741
|
+
var _seq = 0;
|
|
742
|
+
var InvariantViolation = class extends Error {
|
|
743
|
+
constructor(report) {
|
|
744
|
+
super(`[${report.invariant_id}@${report.boundary}] ${report.reason}`);
|
|
745
|
+
this.name = "InvariantViolation";
|
|
746
|
+
this.report = report;
|
|
747
|
+
}
|
|
748
|
+
};
|
|
749
|
+
function hashInput(value) {
|
|
750
|
+
const bytes = typeof value === "string" ? value : JSON.stringify(value) ?? "";
|
|
751
|
+
return crypto4.createHash("sha256").update(bytes, "utf8").digest("hex");
|
|
752
|
+
}
|
|
753
|
+
function violate(invariant_id, boundary, reason, input) {
|
|
754
|
+
throw new InvariantViolation({
|
|
755
|
+
invariant_id,
|
|
756
|
+
boundary,
|
|
757
|
+
reason,
|
|
758
|
+
input_hash: hashInput(input),
|
|
759
|
+
timestamp_seq: ++_seq
|
|
760
|
+
});
|
|
761
|
+
}
|
|
762
|
+
|
|
763
|
+
// src/sealed-vm.ts
|
|
764
|
+
var FORBIDDEN_GLOBALS = [
|
|
765
|
+
"Date.now",
|
|
766
|
+
"Math.random"
|
|
767
|
+
];
|
|
768
|
+
var SEALED_SCOPE_FILES = [
|
|
769
|
+
"packages/execution/src/execute.ts",
|
|
770
|
+
"packages/execution/src/pipeline.ts",
|
|
771
|
+
"packages/execution/src/canonical-signing.ts",
|
|
772
|
+
"packages/bundle/src/canonicalize.ts",
|
|
773
|
+
"packages/bundle/src/hash.ts"
|
|
774
|
+
];
|
|
775
|
+
function governingTime(provided) {
|
|
776
|
+
if (provided && provided.length > 0) {
|
|
777
|
+
return provided;
|
|
778
|
+
}
|
|
779
|
+
return (/* @__PURE__ */ new Date()).toISOString();
|
|
780
|
+
}
|
|
781
|
+
|
|
782
|
+
// src/execute-from-signals.ts
|
|
783
|
+
import * as crypto5 from "crypto";
|
|
784
|
+
|
|
785
|
+
// src/execute-with-redis.ts
|
|
786
|
+
async function executeWithRedis(context, redisStore) {
|
|
787
|
+
await redisStore.markExecuted(
|
|
788
|
+
context.token.execution_id
|
|
789
|
+
);
|
|
790
|
+
const memoryStore = new MemoryReplayStore();
|
|
791
|
+
return executeDecision(context, memoryStore);
|
|
792
|
+
}
|
|
793
|
+
|
|
794
|
+
// src/canonical-json.ts
|
|
795
|
+
function canonicalize5(value) {
|
|
796
|
+
return JSON.stringify(sortValue(value));
|
|
797
|
+
}
|
|
798
|
+
function sortValue(value) {
|
|
799
|
+
if (Array.isArray(value)) {
|
|
800
|
+
return value.map(sortValue);
|
|
801
|
+
}
|
|
802
|
+
if (value && typeof value === "object") {
|
|
803
|
+
const sorted = {};
|
|
804
|
+
for (const key of Object.keys(value).sort()) {
|
|
805
|
+
sorted[key] = sortValue(value[key]);
|
|
806
|
+
}
|
|
807
|
+
return sorted;
|
|
808
|
+
}
|
|
809
|
+
return value;
|
|
810
|
+
}
|
|
811
|
+
|
|
812
|
+
// src/execute-from-signals.ts
|
|
813
|
+
async function executeFromSignals(input, signer, verifier, replayStore) {
|
|
814
|
+
try {
|
|
815
|
+
const policy = loadPolicy(
|
|
816
|
+
input.policyId,
|
|
817
|
+
input.policyVersion
|
|
818
|
+
);
|
|
819
|
+
validateSignalsStrict(input.signals, policy);
|
|
820
|
+
const decision = evaluatePolicy(policy, input.signals);
|
|
821
|
+
if (decision.status !== "decided" || !decision.outcome) {
|
|
822
|
+
throw new Error(
|
|
823
|
+
"[SYS-004] Invalid policy: execution must resolve to decided"
|
|
824
|
+
);
|
|
825
|
+
}
|
|
826
|
+
if (!decision.rule_id) {
|
|
827
|
+
throw new Error(
|
|
828
|
+
"[SYS-005] Invalid decision: rule_id required"
|
|
829
|
+
);
|
|
830
|
+
}
|
|
831
|
+
const canonicalSignals = canonicalize5(input.signals);
|
|
832
|
+
const executionId = crypto5.createHash("sha256").update(
|
|
833
|
+
JSON.stringify({
|
|
834
|
+
policyId: input.policyId,
|
|
835
|
+
policyVersion: input.policyVersion,
|
|
836
|
+
signals: canonicalSignals
|
|
837
|
+
})
|
|
838
|
+
).digest("hex");
|
|
839
|
+
const runtimeManifest = getRuntimeManifest();
|
|
840
|
+
const token = issueToken({
|
|
841
|
+
execution_id: executionId,
|
|
842
|
+
policy_id: input.policyId,
|
|
843
|
+
decision_payload: decision.outcome,
|
|
844
|
+
schema_version: policy.schemaVersion,
|
|
845
|
+
runtime_version: runtimeManifest.runtime_version
|
|
846
|
+
});
|
|
847
|
+
const tokenSignature = signExecutionToken(token, signer);
|
|
848
|
+
const runtimeRequirements = {
|
|
849
|
+
required_capabilities: [],
|
|
850
|
+
supported_runtime_versions: [
|
|
851
|
+
runtimeManifest.runtime_version
|
|
852
|
+
],
|
|
853
|
+
supported_schema_versions: [
|
|
854
|
+
policy.schemaVersion
|
|
855
|
+
]
|
|
856
|
+
};
|
|
857
|
+
const action = decision.outcome.action;
|
|
858
|
+
const requiresOverride = decision.outcome.requires_override;
|
|
859
|
+
let execution_state;
|
|
860
|
+
if (requiresOverride) {
|
|
861
|
+
execution_state = "pending_override";
|
|
862
|
+
} else {
|
|
863
|
+
execution_state = action === "approve" ? "completed" : "blocked";
|
|
864
|
+
}
|
|
865
|
+
if (execution_state === "pending_override") {
|
|
866
|
+
if (!replayStore.set) {
|
|
867
|
+
throw new Error(
|
|
868
|
+
"[SYS-020] Store does not support pending execution storage"
|
|
869
|
+
);
|
|
870
|
+
}
|
|
871
|
+
await replayStore.set(
|
|
872
|
+
`pending:${executionId}`,
|
|
873
|
+
JSON.stringify({
|
|
874
|
+
token,
|
|
875
|
+
token_signature: tokenSignature,
|
|
876
|
+
runtime_manifest: runtimeManifest,
|
|
877
|
+
runtime_requirements: runtimeRequirements
|
|
878
|
+
})
|
|
879
|
+
);
|
|
880
|
+
return {
|
|
881
|
+
status: "pending_override",
|
|
882
|
+
execution_id: executionId,
|
|
883
|
+
decision,
|
|
884
|
+
requires_override: true
|
|
885
|
+
};
|
|
886
|
+
}
|
|
887
|
+
let execution;
|
|
888
|
+
try {
|
|
889
|
+
execution = await executeWithRedis(
|
|
890
|
+
{
|
|
891
|
+
token,
|
|
892
|
+
token_signature: tokenSignature,
|
|
893
|
+
signer,
|
|
894
|
+
verifier,
|
|
895
|
+
runtime_manifest: runtimeManifest,
|
|
896
|
+
runtime_requirements: runtimeRequirements
|
|
897
|
+
},
|
|
898
|
+
replayStore
|
|
899
|
+
);
|
|
900
|
+
} catch (err) {
|
|
901
|
+
const message = err instanceof Error ? err.message : "Unknown error";
|
|
902
|
+
if (message.includes("Replay attack detected")) {
|
|
903
|
+
return {
|
|
904
|
+
status: "success",
|
|
905
|
+
execution_id: executionId,
|
|
906
|
+
decision,
|
|
907
|
+
execution_state,
|
|
908
|
+
requires_override: false,
|
|
909
|
+
replay: true
|
|
910
|
+
};
|
|
911
|
+
}
|
|
912
|
+
throw err;
|
|
913
|
+
}
|
|
914
|
+
return {
|
|
915
|
+
status: "success",
|
|
916
|
+
execution_id: executionId,
|
|
917
|
+
decision,
|
|
918
|
+
execution_state,
|
|
919
|
+
requires_override: false,
|
|
920
|
+
signature: execution.signature
|
|
921
|
+
};
|
|
922
|
+
} catch (err) {
|
|
923
|
+
return {
|
|
924
|
+
status: "error",
|
|
925
|
+
error: err instanceof Error ? err.message : "Unknown error"
|
|
926
|
+
};
|
|
927
|
+
}
|
|
928
|
+
}
|
|
929
|
+
|
|
930
|
+
// src/execute-batch.ts
|
|
931
|
+
async function executeBatch(records, signer, verifier, replayStore) {
|
|
932
|
+
const outputs = [];
|
|
933
|
+
for (const record of records) {
|
|
934
|
+
try {
|
|
935
|
+
const output = await executeFromSignals(
|
|
936
|
+
record,
|
|
937
|
+
signer,
|
|
938
|
+
verifier,
|
|
939
|
+
replayStore
|
|
940
|
+
);
|
|
941
|
+
outputs.push({
|
|
942
|
+
input: record,
|
|
943
|
+
output
|
|
944
|
+
});
|
|
945
|
+
} catch (err) {
|
|
946
|
+
outputs.push({
|
|
947
|
+
input: record,
|
|
948
|
+
output: {
|
|
949
|
+
status: "error",
|
|
950
|
+
error: err instanceof Error ? err.message : "Unknown error"
|
|
951
|
+
}
|
|
952
|
+
});
|
|
953
|
+
}
|
|
954
|
+
}
|
|
955
|
+
return outputs;
|
|
956
|
+
}
|
|
957
|
+
|
|
958
|
+
// src/redis-replay-store.ts
|
|
959
|
+
import Redis from "ioredis";
|
|
960
|
+
var RedisReplayStore = class {
|
|
961
|
+
constructor(url) {
|
|
962
|
+
this.client = new Redis(url);
|
|
963
|
+
}
|
|
964
|
+
// -----------------------------
|
|
965
|
+
// Replay protection
|
|
966
|
+
// -----------------------------
|
|
967
|
+
async hasExecuted(executionId) {
|
|
968
|
+
const res = await this.client.exists(`exec:${executionId}`);
|
|
969
|
+
return res === 1;
|
|
970
|
+
}
|
|
971
|
+
async markExecuted(executionId) {
|
|
972
|
+
const result = await this.client.set(
|
|
973
|
+
`exec:${executionId}`,
|
|
974
|
+
"1",
|
|
975
|
+
"NX"
|
|
976
|
+
);
|
|
977
|
+
if (result !== "OK") {
|
|
978
|
+
throw new Error(
|
|
979
|
+
`[INV-013@replay] Replay detected: execution_id ${executionId} has already been consumed`
|
|
980
|
+
);
|
|
981
|
+
}
|
|
982
|
+
}
|
|
983
|
+
// -----------------------------
|
|
984
|
+
// KV storage (for override)
|
|
985
|
+
// -----------------------------
|
|
986
|
+
async get(key) {
|
|
987
|
+
return this.client.get(key);
|
|
988
|
+
}
|
|
989
|
+
async set(key, value) {
|
|
990
|
+
await this.client.set(key, value);
|
|
991
|
+
}
|
|
992
|
+
async del(key) {
|
|
993
|
+
await this.client.del(key);
|
|
994
|
+
}
|
|
995
|
+
async close() {
|
|
996
|
+
await this.client.quit();
|
|
997
|
+
}
|
|
998
|
+
};
|
|
999
|
+
|
|
1000
|
+
// src/resolve-override.ts
|
|
1001
|
+
async function resolveOverride(executionId, replayStore, signer, verifier) {
|
|
1002
|
+
const raw = await replayStore.get(`pending:${executionId}`);
|
|
1003
|
+
if (!raw) {
|
|
1004
|
+
throw new Error(
|
|
1005
|
+
`[SYS-021] No pending execution found for ${executionId}`
|
|
1006
|
+
);
|
|
1007
|
+
}
|
|
1008
|
+
const stored = JSON.parse(raw);
|
|
1009
|
+
const execution = await executeWithRedis(
|
|
1010
|
+
{
|
|
1011
|
+
token: stored.token,
|
|
1012
|
+
token_signature: stored.token_signature,
|
|
1013
|
+
signer,
|
|
1014
|
+
verifier,
|
|
1015
|
+
runtime_manifest: stored.runtime_manifest,
|
|
1016
|
+
runtime_requirements: stored.runtime_requirements
|
|
1017
|
+
},
|
|
1018
|
+
replayStore
|
|
1019
|
+
);
|
|
1020
|
+
await replayStore.del(`pending:${executionId}`);
|
|
1021
|
+
return {
|
|
1022
|
+
status: "success",
|
|
1023
|
+
execution_id: executionId,
|
|
1024
|
+
signature: execution.signature,
|
|
1025
|
+
resolved: true
|
|
1026
|
+
};
|
|
1027
|
+
}
|
|
1028
|
+
export {
|
|
1029
|
+
FORBIDDEN_GLOBALS,
|
|
1030
|
+
INVARIANT_REGISTRY,
|
|
1031
|
+
InvariantViolation,
|
|
1032
|
+
LocalSigner,
|
|
1033
|
+
LocalVerifier,
|
|
1034
|
+
MemoryReplayStore,
|
|
1035
|
+
RedisReplayStore,
|
|
1036
|
+
SEALED_SCOPE_FILES,
|
|
1037
|
+
canonicalize5 as canonicalize,
|
|
1038
|
+
evaluateDryRun,
|
|
1039
|
+
evaluatePolicy,
|
|
1040
|
+
executeBatch,
|
|
1041
|
+
executeDecision,
|
|
1042
|
+
executeFromSignals,
|
|
1043
|
+
getRuntimeManifest,
|
|
1044
|
+
governingTime,
|
|
1045
|
+
hashInput,
|
|
1046
|
+
hashRuntime,
|
|
1047
|
+
issueToken,
|
|
1048
|
+
loadPolicy,
|
|
1049
|
+
resolveOverride,
|
|
1050
|
+
runtimeManifestDefinition,
|
|
1051
|
+
signExecutionToken,
|
|
1052
|
+
signRuntimeManifest,
|
|
1053
|
+
stageExecute,
|
|
1054
|
+
stageSign,
|
|
1055
|
+
stageVerify,
|
|
1056
|
+
verifyAuditChain,
|
|
1057
|
+
verifyAuditEntry,
|
|
1058
|
+
verifyExecutionToken,
|
|
1059
|
+
verifyRuntimeManifest,
|
|
1060
|
+
verifyRuntimePolicy,
|
|
1061
|
+
violate
|
|
1062
|
+
};
|
|
1063
|
+
//# sourceMappingURL=index.js.map
|