@primust/artifact-core 1.0.0 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (54) hide show
  1. package/LICENSE +93 -0
  2. package/dist/canonical.d.ts +11 -0
  3. package/dist/canonical.d.ts.map +1 -1
  4. package/dist/canonical.js +92 -0
  5. package/dist/canonical.js.map +1 -1
  6. package/dist/commitment.d.ts +29 -8
  7. package/dist/commitment.d.ts.map +1 -1
  8. package/dist/commitment.js +45 -17
  9. package/dist/commitment.js.map +1 -1
  10. package/dist/commitment.test.js +14 -3
  11. package/dist/commitment.test.js.map +1 -1
  12. package/dist/index.d.ts +8 -1
  13. package/dist/index.d.ts.map +1 -1
  14. package/dist/index.js +4 -1
  15. package/dist/index.js.map +1 -1
  16. package/dist/metadata_source.d.ts +4 -0
  17. package/dist/metadata_source.d.ts.map +1 -0
  18. package/dist/metadata_source.js +54 -0
  19. package/dist/metadata_source.js.map +1 -0
  20. package/dist/metadata_source.test.d.ts +2 -0
  21. package/dist/metadata_source.test.d.ts.map +1 -0
  22. package/dist/metadata_source.test.js +29 -0
  23. package/dist/metadata_source.test.js.map +1 -0
  24. package/dist/reversibility_taxonomy.d.ts +23 -0
  25. package/dist/reversibility_taxonomy.d.ts.map +1 -0
  26. package/dist/reversibility_taxonomy.js +208 -0
  27. package/dist/reversibility_taxonomy.js.map +1 -0
  28. package/dist/reversibility_taxonomy.test.d.ts +2 -0
  29. package/dist/reversibility_taxonomy.test.d.ts.map +1 -0
  30. package/dist/reversibility_taxonomy.test.js +146 -0
  31. package/dist/reversibility_taxonomy.test.js.map +1 -0
  32. package/dist/signing.d.ts.map +1 -1
  33. package/dist/signing.js +30 -6
  34. package/dist/signing.js.map +1 -1
  35. package/dist/trust_edge_mapping.d.ts +12 -0
  36. package/dist/trust_edge_mapping.d.ts.map +1 -0
  37. package/dist/trust_edge_mapping.js +88 -0
  38. package/dist/trust_edge_mapping.js.map +1 -0
  39. package/dist/trust_edge_mapping.test.d.ts +2 -0
  40. package/dist/trust_edge_mapping.test.d.ts.map +1 -0
  41. package/dist/trust_edge_mapping.test.js +86 -0
  42. package/dist/trust_edge_mapping.test.js.map +1 -0
  43. package/dist/types/artifact.d.ts +65 -4
  44. package/dist/types/artifact.d.ts.map +1 -1
  45. package/dist/types/proof_artifact.d.ts +52 -0
  46. package/dist/types/proof_artifact.d.ts.map +1 -0
  47. package/dist/types/proof_artifact.js +12 -0
  48. package/dist/types/proof_artifact.js.map +1 -0
  49. package/dist/validate-artifact.d.ts.map +1 -1
  50. package/dist/validate-artifact.js +88 -10
  51. package/dist/validate-artifact.js.map +1 -1
  52. package/dist/validate-artifact.test.js +16 -2
  53. package/dist/validate-artifact.test.js.map +1 -1
  54. package/package.json +13 -7
@@ -0,0 +1,54 @@
1
+ // metadata_source enum — TypeScript sibling of
2
+ // `packages/primust-checks/src/primust_checks/metadata_source.py`.
3
+ //
4
+ // Single source of truth for the metadata_source CHECK enum on
5
+ // check_execution_records (migration 179) on the TS side.
6
+ //
7
+ // Each of the four values is a PRECISE, NARROW provenance claim —
8
+ // not a fallback ladder. The values' trust meaning depends on staying
9
+ // narrow.
10
+ //
11
+ // - 'hook_observed' — A runtime intercept (CC / Cursor / Anthropic
12
+ // Agent SDK lifecycle hook) saw this at the framework boundary.
13
+ // Substrate witness; strongest non-repudiation.
14
+ //
15
+ // - 'sdk_decomposed' — An SDK adapter derived the bounded metadata
16
+ // in-process (LLM quadruple, enforcement attribution, redaction).
17
+ // Adapter composition — observed and shaped, not relayed.
18
+ //
19
+ // - 'sdk_caller_supplied' — App code passed metadata args to
20
+ // run.record() and the SDK relayed without deriving or
21
+ // independently observing. Caller-as-source-of-truth. Honest,
22
+ // narrow; weaker evidence than hook_observed (no substrate
23
+ // witness) or sdk_decomposed (no adapter composition).
24
+ //
25
+ // - 'hook_and_sdk_concordant' — Both layers independently confirmed
26
+ // the same fact via the trace_context join (Phase 3+). Cross-
27
+ // checked; highest trust. Back-filled server-side.
28
+ //
29
+ // - NULL — RESERVED for legacy pre-179 rows and aggregator-emitted
30
+ // records with no single per-record derivation. No new emitter
31
+ // should land NULL. A NULL on a fresh record is an emitter bug.
32
+ //
33
+ // SI-1: enum-constrained string, never content.
34
+ export const METADATA_SOURCE_VALUES = [
35
+ // Runtime intercept saw the event at the framework boundary.
36
+ // Substrate witness; strongest non-repudiation.
37
+ 'hook_observed',
38
+ // SDK adapter derived the bounded metadata in-process (LLM
39
+ // quadruple, enforcement attribution, redaction). Adapter
40
+ // composition — observed and shaped, not relayed.
41
+ 'sdk_decomposed',
42
+ // App code passed metadata args to run.record() and the SDK
43
+ // relayed without deriving or independently observing. Honest,
44
+ // narrow; weaker than hook_observed / sdk_decomposed.
45
+ 'sdk_caller_supplied',
46
+ // Both layers independently confirmed the same fact via the
47
+ // trace_context join (Phase 3+). Cross-checked; highest trust.
48
+ // Back-filled server-side; never emitted directly by a single layer.
49
+ 'hook_and_sdk_concordant',
50
+ ];
51
+ export function isMetadataSource(value) {
52
+ return (typeof value === 'string' && METADATA_SOURCE_VALUES.includes(value));
53
+ }
54
+ //# sourceMappingURL=metadata_source.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"metadata_source.js","sourceRoot":"","sources":["../src/metadata_source.ts"],"names":[],"mappings":"AAAA,+CAA+C;AAC/C,mEAAmE;AACnE,EAAE;AACF,+DAA+D;AAC/D,0DAA0D;AAC1D,EAAE;AACF,kEAAkE;AAClE,sEAAsE;AACtE,UAAU;AACV,EAAE;AACF,qEAAqE;AACrE,oEAAoE;AACpE,oDAAoD;AACpD,EAAE;AACF,qEAAqE;AACrE,sEAAsE;AACtE,8DAA8D;AAC9D,EAAE;AACF,+DAA+D;AAC/D,2DAA2D;AAC3D,kEAAkE;AAClE,+DAA+D;AAC/D,2DAA2D;AAC3D,EAAE;AACF,sEAAsE;AACtE,kEAAkE;AAClE,uDAAuD;AACvD,EAAE;AACF,qEAAqE;AACrE,mEAAmE;AACnE,oEAAoE;AACpE,EAAE;AACF,gDAAgD;AAEhD,MAAM,CAAC,MAAM,sBAAsB,GAAG;IACpC,6DAA6D;IAC7D,gDAAgD;IAChD,eAAe;IAEf,2DAA2D;IAC3D,0DAA0D;IAC1D,kDAAkD;IAClD,gBAAgB;IAEhB,4DAA4D;IAC5D,+DAA+D;IAC/D,sDAAsD;IACtD,qBAAqB;IAErB,4DAA4D;IAC5D,+DAA+D;IAC/D,qEAAqE;IACrE,yBAAyB;CACjB,CAAC;AAIX,MAAM,UAAU,gBAAgB,CAAC,KAAc;IAC7C,OAAO,CACL,OAAO,KAAK,KAAK,QAAQ,IAAK,sBAA4C,CAAC,QAAQ,CAAC,KAAK,CAAC,CAC3F,CAAC;AACJ,CAAC"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=metadata_source.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"metadata_source.test.d.ts","sourceRoot":"","sources":["../src/metadata_source.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,29 @@
1
+ import { describe, it, expect } from 'vitest';
2
+ import { METADATA_SOURCE_VALUES, isMetadataSource } from './metadata_source.js';
3
+ describe('metadata_source', () => {
4
+ it('has exactly the four canonical values from migration 179', () => {
5
+ expect(new Set(METADATA_SOURCE_VALUES)).toEqual(new Set([
6
+ 'hook_observed',
7
+ 'sdk_decomposed',
8
+ 'sdk_caller_supplied',
9
+ 'hook_and_sdk_concordant',
10
+ ]));
11
+ });
12
+ it('isMetadataSource accepts all four enum strings', () => {
13
+ for (const v of METADATA_SOURCE_VALUES) {
14
+ expect(isMetadataSource(v)).toBe(true);
15
+ }
16
+ });
17
+ it('rejects unknown strings (including the distinct `source` enum)', () => {
18
+ expect(isMetadataSource('garbage')).toBe(false);
19
+ expect(isMetadataSource('hook')).toBe(false); // bare 'hook' is `source`, not metadata_source
20
+ expect(isMetadataSource('sdk')).toBe(false);
21
+ });
22
+ it('rejects non-strings', () => {
23
+ expect(isMetadataSource(null)).toBe(false);
24
+ expect(isMetadataSource(42)).toBe(false);
25
+ expect(isMetadataSource([])).toBe(false);
26
+ expect(isMetadataSource({ value: 'hook_observed' })).toBe(false);
27
+ });
28
+ });
29
+ //# sourceMappingURL=metadata_source.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"metadata_source.test.js","sourceRoot":"","sources":["../src/metadata_source.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAC9C,OAAO,EAAE,sBAAsB,EAAE,gBAAgB,EAAE,MAAM,sBAAsB,CAAC;AAEhF,QAAQ,CAAC,iBAAiB,EAAE,GAAG,EAAE;IAC/B,EAAE,CAAC,0DAA0D,EAAE,GAAG,EAAE;QAClE,MAAM,CAAC,IAAI,GAAG,CAAC,sBAAsB,CAAC,CAAC,CAAC,OAAO,CAC7C,IAAI,GAAG,CAAC;YACN,eAAe;YACf,gBAAgB;YAChB,qBAAqB;YACrB,yBAAyB;SAC1B,CAAC,CACH,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gDAAgD,EAAE,GAAG,EAAE;QACxD,KAAK,MAAM,CAAC,IAAI,sBAAsB,EAAE,CAAC;YACvC,MAAM,CAAC,gBAAgB,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACzC,CAAC;IACH,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,gEAAgE,EAAE,GAAG,EAAE;QACxE,MAAM,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAChD,MAAM,CAAC,gBAAgB,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,+CAA+C;QAC7F,MAAM,CAAC,gBAAgB,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC9C,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,qBAAqB,EAAE,GAAG,EAAE;QAC7B,MAAM,CAAC,gBAAgB,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAC3C,MAAM,CAAC,gBAAgB,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACzC,MAAM,CAAC,gBAAgB,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QACzC,MAAM,CAAC,gBAAgB,CAAC,EAAE,KAAK,EAAE,eAAe,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IACnE,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
@@ -0,0 +1,23 @@
1
+ export declare const TAXONOMY_VERSION: "1.0.0";
2
+ export declare const REVERSIBILITY_CLASSES: readonly ["reversible", "append_only", "external_side_effect", "irreversible", "unknown"];
3
+ export type ReversibilityClass = (typeof REVERSIBILITY_CLASSES)[number];
4
+ export declare function isReversibilityClass(v: unknown): v is ReversibilityClass;
5
+ export interface ClassifyOptions {
6
+ overrides?: Record<string, string>;
7
+ }
8
+ /**
9
+ * Classify an outbound action by `(target_system_kind, operation)`.
10
+ *
11
+ * Lookup order:
12
+ * 1. Customer override for the exact (kind, op) pair.
13
+ * 2. System default for the exact (kind, op) pair.
14
+ * 3. Per-kind fallback.
15
+ * 4. `'unknown'`.
16
+ */
17
+ export declare function classify(target_system_kind: string, operation: string, options?: ClassifyOptions): ReversibilityClass;
18
+ /**
19
+ * True if this kind has real (non-`'unknown'`) classifications in the
20
+ * system defaults. Used by the Phase 1 acceptance gate.
21
+ */
22
+ export declare function isWedgeSurfaceCovered(target_system_kind: string): boolean;
23
+ //# sourceMappingURL=reversibility_taxonomy.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reversibility_taxonomy.d.ts","sourceRoot":"","sources":["../src/reversibility_taxonomy.ts"],"names":[],"mappings":"AAcA,eAAO,MAAM,gBAAgB,EAAG,OAAgB,CAAC;AAEjD,eAAO,MAAM,qBAAqB,2FAMxB,CAAC;AAEX,MAAM,MAAM,kBAAkB,GAAG,CAAC,OAAO,qBAAqB,CAAC,CAAC,MAAM,CAAC,CAAC;AAGxE,wBAAgB,oBAAoB,CAAC,CAAC,EAAE,OAAO,GAAG,CAAC,IAAI,kBAAkB,CAExE;AAgKD,MAAM,WAAW,eAAe;IAI9B,SAAS,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACpC;AAED;;;;;;;;GAQG;AACH,wBAAgB,QAAQ,CACtB,kBAAkB,EAAE,MAAM,EAC1B,SAAS,EAAE,MAAM,EACjB,OAAO,GAAE,eAAoB,GAC5B,kBAAkB,CAcpB;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,kBAAkB,EAAE,MAAM,GAAG,OAAO,CAMzE"}
@@ -0,0 +1,208 @@
1
+ // Reversibility taxonomy for outbound-action records.
2
+ //
3
+ // TypeScript sibling of
4
+ // `packages/primust-checks/src/primust_checks/reversibility_taxonomy.py`.
5
+ // Both implementations stamp the same `TAXONOMY_VERSION` so a credential
6
+ // classified by either side is comparable.
7
+ //
8
+ // Implements the system-default classification referenced by
9
+ // `docs/v30/foundation/OUTBOUND_ACTION_EVIDENCE_SPEC_v0_1.md` §1.2 and §2.5
10
+ // and `AGENT_MANIFEST_SPEC_v0_1.md` §3.3 (`reversibility_overrides`).
11
+ //
12
+ // SI-1: this module emits only enum / count / hash / typed-reference values.
13
+ // The taxonomy itself is content-free.
14
+ export const TAXONOMY_VERSION = '1.0.0';
15
+ export const REVERSIBILITY_CLASSES = [
16
+ 'reversible',
17
+ 'append_only',
18
+ 'external_side_effect',
19
+ 'irreversible',
20
+ 'unknown',
21
+ ];
22
+ // Type guard for safe parsing of customer-supplied override strings.
23
+ export function isReversibilityClass(v) {
24
+ return typeof v === 'string' && REVERSIBILITY_CLASSES.includes(v);
25
+ }
26
+ // Operation-specific defaults, keyed by `${kind}::${operation}`.
27
+ //
28
+ // Operation strings follow the spec's per-adapter convention; see the
29
+ // Python sibling for the full convention table.
30
+ const DEFAULTS = {
31
+ // ───────── AWS API ─────────
32
+ 'aws_api::GetObject': 'reversible',
33
+ 'aws_api::ListObjects': 'reversible',
34
+ 'aws_api::ListObjectsV2': 'reversible',
35
+ 'aws_api::HeadObject': 'reversible',
36
+ 'aws_api::ListBuckets': 'reversible',
37
+ 'aws_api::DescribeInstances': 'reversible',
38
+ 'aws_api::DescribeDBInstances': 'reversible',
39
+ 'aws_api::GetItem': 'reversible',
40
+ 'aws_api::Query': 'reversible',
41
+ 'aws_api::Scan': 'reversible',
42
+ 'aws_api::PutObject': 'append_only',
43
+ 'aws_api::PutItem': 'append_only',
44
+ 'aws_api::CreateBucket': 'append_only',
45
+ 'aws_api::CreateTable': 'append_only',
46
+ 'aws_api::RunInstances': 'append_only',
47
+ 'aws_api::CreateDBInstance': 'append_only',
48
+ 'aws_api::SendEmail': 'external_side_effect',
49
+ 'aws_api::Publish': 'external_side_effect',
50
+ 'aws_api::SendMessage': 'external_side_effect',
51
+ 'aws_api::Invoke': 'external_side_effect',
52
+ 'aws_api::RebootInstances': 'external_side_effect',
53
+ 'aws_api::StopInstances': 'external_side_effect',
54
+ 'aws_api::StartInstances': 'external_side_effect',
55
+ 'aws_api::DeleteObject': 'irreversible',
56
+ 'aws_api::DeleteObjects': 'irreversible',
57
+ 'aws_api::DeleteBucket': 'irreversible',
58
+ 'aws_api::DeleteTable': 'irreversible',
59
+ 'aws_api::DeleteItem': 'irreversible',
60
+ 'aws_api::TerminateInstances': 'irreversible',
61
+ 'aws_api::DeleteDBInstance': 'irreversible',
62
+ // ───────── Stripe API (per spec §2.5) ─────────
63
+ 'stripe_api::charges.list': 'reversible',
64
+ 'stripe_api::charges.retrieve': 'reversible',
65
+ 'stripe_api::customers.list': 'reversible',
66
+ 'stripe_api::customers.retrieve': 'reversible',
67
+ 'stripe_api::balance.retrieve': 'reversible',
68
+ 'stripe_api::charges.create': 'irreversible',
69
+ 'stripe_api::payment_intents.confirm': 'irreversible',
70
+ 'stripe_api::charges.refund': 'append_only',
71
+ 'stripe_api::customers.create': 'append_only',
72
+ 'stripe_api::subscriptions.create': 'append_only',
73
+ 'stripe_api::invoices.create': 'append_only',
74
+ 'stripe_api::customers.update': 'external_side_effect',
75
+ 'stripe_api::subscriptions.update': 'external_side_effect',
76
+ 'stripe_api::webhooks.create': 'external_side_effect',
77
+ 'stripe_api::customers.delete': 'irreversible',
78
+ 'stripe_api::subscriptions.delete': 'irreversible',
79
+ // ───────── GitHub API ─────────
80
+ 'github_api::GET /repos/{owner}/{repo}': 'reversible',
81
+ 'github_api::GET /repos/{owner}/{repo}/issues': 'reversible',
82
+ 'github_api::GET /repos/{owner}/{repo}/pulls': 'reversible',
83
+ 'github_api::GET /repos/{owner}/{repo}/contents/{path}': 'reversible',
84
+ 'github_api::POST /repos/{owner}/{repo}/issues': 'append_only',
85
+ 'github_api::POST /repos/{owner}/{repo}/pulls': 'append_only',
86
+ 'github_api::POST /repos/{owner}/{repo}/issues/{number}/comments': 'append_only',
87
+ 'github_api::POST /repos/{owner}/{repo}/pulls/{number}/reviews': 'append_only',
88
+ 'github_api::POST /repos/{owner}/{repo}/pulls/{number}/merge': 'external_side_effect',
89
+ 'github_api::PATCH /repos/{owner}/{repo}/issues/{number}': 'reversible',
90
+ 'github_api::PATCH /repos/{owner}/{repo}/pulls/{number}': 'reversible',
91
+ 'github_api::PUT /repos/{owner}/{repo}/contents/{path}': 'append_only',
92
+ 'github_api::DELETE /repos/{owner}/{repo}/contents/{path}': 'irreversible',
93
+ 'github_api::DELETE /repos/{owner}/{repo}': 'irreversible',
94
+ 'github_api::DELETE /repos/{owner}/{repo}/branches/{branch}': 'reversible',
95
+ // ───────── Salesforce REST ─────────
96
+ 'salesforce_rest::GET /sobjects/Account/{id}': 'reversible',
97
+ 'salesforce_rest::GET /sobjects/Task/{id}': 'reversible',
98
+ 'salesforce_rest::GET /query': 'reversible',
99
+ 'salesforce_rest::POST /sobjects/Task': 'append_only',
100
+ 'salesforce_rest::POST /sobjects/Account': 'append_only',
101
+ 'salesforce_rest::POST /sobjects/Lead': 'append_only',
102
+ 'salesforce_rest::POST /sobjects/Contact': 'append_only',
103
+ 'salesforce_rest::POST /sobjects/Opportunity': 'append_only',
104
+ 'salesforce_rest::POST /sobjects/Case': 'append_only',
105
+ 'salesforce_rest::PATCH /sobjects/Account/{id}': 'reversible',
106
+ 'salesforce_rest::PATCH /sobjects/Task/{id}': 'reversible',
107
+ 'salesforce_rest::DELETE /sobjects/Account/{id}': 'irreversible',
108
+ 'salesforce_rest::DELETE /sobjects/Task/{id}': 'irreversible',
109
+ // ───────── Slack ─────────
110
+ 'slack::conversations.history': 'reversible',
111
+ 'slack::conversations.list': 'reversible',
112
+ 'slack::users.list': 'reversible',
113
+ 'slack::chat.postMessage': 'external_side_effect',
114
+ 'slack::chat.postEphemeral': 'external_side_effect',
115
+ 'slack::chat.update': 'external_side_effect',
116
+ 'slack::files.upload': 'append_only',
117
+ 'slack::conversations.invite': 'external_side_effect',
118
+ 'slack::conversations.kick': 'external_side_effect',
119
+ 'slack::conversations.create': 'append_only',
120
+ 'slack::conversations.archive': 'reversible',
121
+ 'slack::chat.delete': 'irreversible',
122
+ // ───────── Kubernetes ─────────
123
+ 'k8s::GET /api/v1/namespaces': 'reversible',
124
+ 'k8s::GET /api/v1/namespaces/{ns}/pods': 'reversible',
125
+ 'k8s::GET /apis/apps/v1/namespaces/{ns}/deployments': 'reversible',
126
+ 'k8s::POST /apis/apps/v1/namespaces/{ns}/deployments': 'append_only',
127
+ 'k8s::POST /api/v1/namespaces/{ns}/configmaps': 'append_only',
128
+ 'k8s::POST /api/v1/namespaces/{ns}/secrets': 'append_only',
129
+ 'k8s::PATCH /apis/apps/v1/namespaces/{ns}/deployments/{name}': 'reversible',
130
+ 'k8s::PATCH /api/v1/namespaces/{ns}/configmaps/{name}': 'reversible',
131
+ 'k8s::DELETE /api/v1/namespaces/{ns}/pods/{name}': 'reversible',
132
+ 'k8s::DELETE /apis/apps/v1/namespaces/{ns}/deployments/{name}': 'irreversible',
133
+ 'k8s::DELETE /api/v1/namespaces/{ns}': 'irreversible',
134
+ 'k8s::DELETE /api/v1/namespaces/{ns}/secrets/{name}': 'irreversible',
135
+ // ───────── Postgres / Snowflake ─────────
136
+ 'postgres::SELECT': 'reversible',
137
+ 'postgres::INSERT': 'append_only',
138
+ 'postgres::UPDATE': 'external_side_effect',
139
+ 'postgres::DELETE': 'irreversible',
140
+ 'postgres::DROP TABLE': 'irreversible',
141
+ 'postgres::TRUNCATE': 'irreversible',
142
+ 'snowflake::SELECT': 'reversible',
143
+ 'snowflake::INSERT': 'append_only',
144
+ 'snowflake::UPDATE': 'external_side_effect',
145
+ 'snowflake::DELETE': 'irreversible',
146
+ 'snowflake::DROP TABLE': 'irreversible',
147
+ // ───────── Vector stores (per spec §1.2) ─────────
148
+ 'pinecone::upsert': 'append_only',
149
+ 'pinecone::delete': 'irreversible',
150
+ 'pinecone::query': 'reversible',
151
+ 'pinecone::fetch': 'reversible',
152
+ 'vector_store::upsert': 'append_only',
153
+ 'vector_store::query': 'reversible',
154
+ 'vector_store::delete': 'irreversible',
155
+ };
156
+ // Per-kind fallback when the exact (kind, op) isn't in DEFAULTS.
157
+ const KIND_DEFAULTS = {
158
+ mcp_tool: 'unknown',
159
+ sdk_tool: 'unknown',
160
+ cli_subprocess: 'unknown',
161
+ anthropic_messages: 'append_only',
162
+ openai_chat: 'append_only',
163
+ bedrock_invoke: 'append_only',
164
+ calibrated_profile: 'append_only',
165
+ approval_gate: 'external_side_effect',
166
+ cli_prompt: 'external_side_effect',
167
+ dashboard_escalation: 'external_side_effect',
168
+ subagent_spawn: 'append_only',
169
+ mcp_sampling: 'append_only',
170
+ cross_org_delegation: 'append_only',
171
+ governance_config_surface: 'external_side_effect',
172
+ filesystem: 'unknown',
173
+ generic_http: 'unknown',
174
+ };
175
+ /**
176
+ * Classify an outbound action by `(target_system_kind, operation)`.
177
+ *
178
+ * Lookup order:
179
+ * 1. Customer override for the exact (kind, op) pair.
180
+ * 2. System default for the exact (kind, op) pair.
181
+ * 3. Per-kind fallback.
182
+ * 4. `'unknown'`.
183
+ */
184
+ export function classify(target_system_kind, operation, options = {}) {
185
+ const key = `${target_system_kind}::${operation}`;
186
+ const override = options.overrides?.[key];
187
+ if (override !== undefined && isReversibilityClass(override)) {
188
+ return override;
189
+ }
190
+ const exact = DEFAULTS[key];
191
+ if (exact !== undefined) {
192
+ return exact;
193
+ }
194
+ return KIND_DEFAULTS[target_system_kind] ?? 'unknown';
195
+ }
196
+ /**
197
+ * True if this kind has real (non-`'unknown'`) classifications in the
198
+ * system defaults. Used by the Phase 1 acceptance gate.
199
+ */
200
+ export function isWedgeSurfaceCovered(target_system_kind) {
201
+ const prefix = `${target_system_kind}::`;
202
+ for (const [k, v] of Object.entries(DEFAULTS)) {
203
+ if (k.startsWith(prefix) && v !== 'unknown')
204
+ return true;
205
+ }
206
+ return false;
207
+ }
208
+ //# sourceMappingURL=reversibility_taxonomy.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reversibility_taxonomy.js","sourceRoot":"","sources":["../src/reversibility_taxonomy.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=reversibility_taxonomy.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reversibility_taxonomy.test.d.ts","sourceRoot":"","sources":["../src/reversibility_taxonomy.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,146 @@
1
+ import { describe, it, expect } from 'vitest';
2
+ import { TAXONOMY_VERSION, REVERSIBILITY_CLASSES, isReversibilityClass, classify, isWedgeSurfaceCovered, } from './reversibility_taxonomy.js';
3
+ describe('reversibility_taxonomy', () => {
4
+ describe('Phase 1 acceptance gate: wedge surfaces', () => {
5
+ const wedge = ['salesforce_rest', 'slack', 'github_api', 'stripe_api', 'k8s', 'aws_api'];
6
+ for (const kind of wedge) {
7
+ it(`${kind} has real (non-unknown) classifications`, () => {
8
+ expect(isWedgeSurfaceCovered(kind)).toBe(true);
9
+ });
10
+ }
11
+ });
12
+ describe('per-spec examples (§2.5)', () => {
13
+ it('stripe charges.create → irreversible', () => {
14
+ expect(classify('stripe_api', 'charges.create')).toBe('irreversible');
15
+ });
16
+ it('stripe customers.update → external_side_effect', () => {
17
+ expect(classify('stripe_api', 'customers.update')).toBe('external_side_effect');
18
+ });
19
+ it('stripe charges.list → reversible', () => {
20
+ expect(classify('stripe_api', 'charges.list')).toBe('reversible');
21
+ });
22
+ it('governance_config_surface default → external_side_effect', () => {
23
+ expect(classify('governance_config_surface', 'edit_settings_json')).toBe('external_side_effect');
24
+ });
25
+ it('vector_store upsert → append_only', () => {
26
+ expect(classify('vector_store', 'upsert')).toBe('append_only');
27
+ });
28
+ });
29
+ describe('AWS', () => {
30
+ it('GetObject → reversible', () => {
31
+ expect(classify('aws_api', 'GetObject')).toBe('reversible');
32
+ });
33
+ it('DeleteBucket → irreversible', () => {
34
+ expect(classify('aws_api', 'DeleteBucket')).toBe('irreversible');
35
+ });
36
+ it('PutObject → append_only', () => {
37
+ expect(classify('aws_api', 'PutObject')).toBe('append_only');
38
+ });
39
+ it('SendEmail → external_side_effect', () => {
40
+ expect(classify('aws_api', 'SendEmail')).toBe('external_side_effect');
41
+ });
42
+ });
43
+ describe('Salesforce', () => {
44
+ it('POST /sobjects/Task → append_only', () => {
45
+ expect(classify('salesforce_rest', 'POST /sobjects/Task')).toBe('append_only');
46
+ });
47
+ it('PATCH /sobjects/Account/{id} → reversible (field audit trail)', () => {
48
+ expect(classify('salesforce_rest', 'PATCH /sobjects/Account/{id}')).toBe('reversible');
49
+ });
50
+ it('DELETE /sobjects/Account/{id} → irreversible', () => {
51
+ expect(classify('salesforce_rest', 'DELETE /sobjects/Account/{id}')).toBe('irreversible');
52
+ });
53
+ });
54
+ describe('Slack', () => {
55
+ it('chat.postMessage → external_side_effect', () => {
56
+ expect(classify('slack', 'chat.postMessage')).toBe('external_side_effect');
57
+ });
58
+ it('conversations.history → reversible', () => {
59
+ expect(classify('slack', 'conversations.history')).toBe('reversible');
60
+ });
61
+ it('chat.delete → irreversible', () => {
62
+ expect(classify('slack', 'chat.delete')).toBe('irreversible');
63
+ });
64
+ });
65
+ describe('Kubernetes', () => {
66
+ it('DELETE pod → reversible (controller recreates)', () => {
67
+ expect(classify('k8s', 'DELETE /api/v1/namespaces/{ns}/pods/{name}')).toBe('reversible');
68
+ });
69
+ it('DELETE deployment → irreversible', () => {
70
+ expect(classify('k8s', 'DELETE /apis/apps/v1/namespaces/{ns}/deployments/{name}')).toBe('irreversible');
71
+ });
72
+ it('DELETE namespace → irreversible', () => {
73
+ expect(classify('k8s', 'DELETE /api/v1/namespaces/{ns}')).toBe('irreversible');
74
+ });
75
+ });
76
+ describe('Postgres', () => {
77
+ it('SELECT → reversible', () => {
78
+ expect(classify('postgres', 'SELECT')).toBe('reversible');
79
+ });
80
+ it('UPDATE → external_side_effect', () => {
81
+ expect(classify('postgres', 'UPDATE')).toBe('external_side_effect');
82
+ });
83
+ it('DELETE → irreversible', () => {
84
+ expect(classify('postgres', 'DELETE')).toBe('irreversible');
85
+ });
86
+ it('DROP TABLE → irreversible', () => {
87
+ expect(classify('postgres', 'DROP TABLE')).toBe('irreversible');
88
+ });
89
+ });
90
+ describe('model surfaces', () => {
91
+ it('anthropic_messages → append_only default', () => {
92
+ expect(classify('anthropic_messages', 'POST /v1/messages')).toBe('append_only');
93
+ });
94
+ it('openai_chat → append_only default', () => {
95
+ expect(classify('openai_chat', 'POST /v1/chat/completions')).toBe('append_only');
96
+ });
97
+ });
98
+ describe('fallback behavior', () => {
99
+ it('unknown kind → unknown', () => {
100
+ expect(classify('not_a_real_kind', 'op')).toBe('unknown');
101
+ });
102
+ it('unmapped op on mcp_tool → unknown (kind default)', () => {
103
+ expect(classify('mcp_tool', 'some_tool_call')).toBe('unknown');
104
+ });
105
+ it('unmapped op on aws → unknown', () => {
106
+ expect(classify('aws_api', 'SomeFutureAction')).toBe('unknown');
107
+ });
108
+ it('human-facing default → external_side_effect', () => {
109
+ expect(classify('approval_gate', 'request')).toBe('external_side_effect');
110
+ });
111
+ });
112
+ describe('customer overrides', () => {
113
+ it('override beats system default', () => {
114
+ expect(classify('stripe_api', 'charges.create', {
115
+ overrides: { 'stripe_api::charges.create': 'reversible' },
116
+ })).toBe('reversible');
117
+ });
118
+ it('invalid override falls back to system default', () => {
119
+ expect(classify('stripe_api', 'charges.create', {
120
+ overrides: { 'stripe_api::charges.create': 'not_a_valid_class' },
121
+ })).toBe('irreversible');
122
+ });
123
+ it('override works for unmapped kind', () => {
124
+ expect(classify('custom_internal_api', 'credit_account', {
125
+ overrides: { 'custom_internal_api::credit_account': 'irreversible' },
126
+ })).toBe('irreversible');
127
+ });
128
+ });
129
+ describe('versioning + SI-1 shape', () => {
130
+ it('TAXONOMY_VERSION is semver', () => {
131
+ expect(TAXONOMY_VERSION).toMatch(/^\d+\.\d+\.\d+$/);
132
+ });
133
+ it('all class values use safe alphabet', () => {
134
+ for (const cls of REVERSIBILITY_CLASSES) {
135
+ expect(cls.replace(/_/g, '')).toMatch(/^[a-z]+$/);
136
+ }
137
+ });
138
+ it('isReversibilityClass type guard works', () => {
139
+ expect(isReversibilityClass('reversible')).toBe(true);
140
+ expect(isReversibilityClass('garbage')).toBe(false);
141
+ expect(isReversibilityClass(null)).toBe(false);
142
+ expect(isReversibilityClass(42)).toBe(false);
143
+ });
144
+ });
145
+ });
146
+ //# sourceMappingURL=reversibility_taxonomy.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reversibility_taxonomy.test.js","sourceRoot":"","sources":["../src/reversibility_taxonomy.test.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"signing.d.ts","sourceRoot":"","sources":["../src/signing.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAMH,OAAO,KAAK,EAAE,YAAY,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAa9E,6CAA6C;AAC7C,iBAAS,WAAW,CAAC,KAAK,EAAE,UAAU,GAAG,MAAM,CAM9C;AAED,gCAAgC;AAChC,iBAAS,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,UAAU,CASjD;AAED;;;;GAIG;AACH,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,MAAM,EAChB,KAAK,EAAE,MAAM,EACb,UAAU,EAAE,UAAU,GACrB;IAAE,YAAY,EAAE,YAAY,CAAC;IAAC,UAAU,EAAE,UAAU,CAAA;CAAE,CAsBxD;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,IAAI,CAClB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,UAAU,EAAE,UAAU,EACtB,YAAY,EAAE,YAAY,GACzB;IAAE,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAAC,iBAAiB,EAAE,iBAAiB,CAAA;CAAE,CAkB7E;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,MAAM,CACpB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,iBAAiB,EAAE,iBAAiB,EACpC,eAAe,EAAE,MAAM,GACtB,OAAO,CAWT;AAED;;;;;;;;;GASG;AACH,wBAAgB,SAAS,CAAC,cAAc,EAAE,YAAY,GAAG;IACvD,aAAa,EAAE,YAAY,CAAC;IAC5B,SAAS,EAAE,YAAY,CAAC;IACxB,aAAa,EAAE,UAAU,CAAC;CAC3B,CAyBA;AAGD,OAAO,EAAE,WAAW,EAAE,aAAa,EAAE,CAAC"}
1
+ {"version":3,"file":"signing.d.ts","sourceRoot":"","sources":["../src/signing.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAMH,OAAO,KAAK,EAAE,YAAY,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAa9E,6CAA6C;AAC7C,iBAAS,WAAW,CAAC,KAAK,EAAE,UAAU,GAAG,MAAM,CAM9C;AAED,gCAAgC;AAChC,iBAAS,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,UAAU,CASjD;AAED;;;;GAIG;AACH,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,MAAM,EAChB,KAAK,EAAE,MAAM,EACb,UAAU,EAAE,UAAU,GACrB;IAAE,YAAY,EAAE,YAAY,CAAC;IAAC,UAAU,EAAE,UAAU,CAAA;CAAE,CAsBxD;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,IAAI,CAClB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,UAAU,EAAE,UAAU,EACtB,YAAY,EAAE,YAAY,GACzB;IAAE,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAAC,iBAAiB,EAAE,iBAAiB,CAAA;CAAE,CAkB7E;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,MAAM,CACpB,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACjC,iBAAiB,EAAE,iBAAiB,EACpC,eAAe,EAAE,MAAM,GACtB,OAAO,CAmCT;AAED;;;;;;;;;GASG;AACH,wBAAgB,SAAS,CAAC,cAAc,EAAE,YAAY,GAAG;IACvD,aAAa,EAAE,YAAY,CAAC;IAC5B,SAAS,EAAE,YAAY,CAAC;IACxB,aAAa,EAAE,UAAU,CAAC;CAC3B,CAyBA;AAGD,OAAO,EAAE,WAAW,EAAE,aAAa,EAAE,CAAC"}
package/dist/signing.js CHANGED
@@ -19,7 +19,7 @@
19
19
  import * as ed from '@noble/ed25519';
20
20
  import { sha512 } from '@noble/hashes/sha512';
21
21
  import { sha256 } from '@noble/hashes/sha256';
22
- import { canonical } from './canonical.js';
22
+ import { canonical, canonicalLegacy } from './canonical.js';
23
23
  // Configure ed25519 to use sha512
24
24
  ed.etc.sha512Sync = (...m) => sha512(ed.etc.concatBytes(...m));
25
25
  /** Generate a cryptographically random hex string */
@@ -117,16 +117,40 @@ export function sign(document, privateKey, signerRecord) {
117
117
  * @returns true if the cryptographic signature is valid
118
118
  */
119
119
  export function verify(document, signatureEnvelope, publicKeyB64Url) {
120
+ let signatureBytes;
121
+ let publicKeyBytes;
120
122
  try {
121
- const canonicalStr = canonical(document);
122
- const hashBytes = sha256(new TextEncoder().encode(canonicalStr));
123
- const signatureBytes = fromBase64Url(signatureEnvelope.signature);
124
- const publicKeyBytes = fromBase64Url(publicKeyB64Url);
125
- return ed.verify(signatureBytes, hashBytes, publicKeyBytes);
123
+ signatureBytes = fromBase64Url(signatureEnvelope.signature);
124
+ publicKeyBytes = fromBase64Url(publicKeyB64Url);
126
125
  }
127
126
  catch {
128
127
  return false;
129
128
  }
129
+ // Try the spec-compliant (ECMA-262) canonical form first; fall back
130
+ // to the legacy Python form that signed VPECs before 2026-04-19.
131
+ // Stored signatures are against whichever form was current at
132
+ // sign-time — new code must still be able to verify legacy VPECs
133
+ // until every customer rolls forward.
134
+ // The legacy form has subtle ambiguity (number formatting, key order)
135
+ // that a malicious prover could exploit; only accept it for signatures
136
+ // claimed to have been produced before the canonical-form cutover.
137
+ const LEGACY_CUTOFF = '2026-04-19';
138
+ const signedAt = signatureEnvelope.signed_at ?? '';
139
+ const legacyAllowed = signedAt !== '' && signedAt.slice(0, 10) < LEGACY_CUTOFF;
140
+ const candidates = legacyAllowed ? [canonical, canonicalLegacy] : [canonical];
141
+ for (const canonFn of candidates) {
142
+ try {
143
+ const canonicalStr = canonFn(document);
144
+ const hashBytes = sha256(new TextEncoder().encode(canonicalStr));
145
+ if (ed.verify(signatureBytes, hashBytes, publicKeyBytes)) {
146
+ return true;
147
+ }
148
+ }
149
+ catch {
150
+ // try next form
151
+ }
152
+ }
153
+ return false;
130
154
  }
131
155
  /**
132
156
  * Rotate a key: create a new kid under the same signer_id.
@@ -1 +1 @@
1
- {"version":3,"file":"signing.js","sourceRoot":"","sources":["../src/signing.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"signing.js","sourceRoot":"","sources":["../src/signing.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,12 @@
1
+ export declare const MAPPING_VERSION: "1.0.0";
2
+ export declare const TRUST_EDGES: readonly ["A2T", "A2M", "A2H", "A2A", "A2S", "A2D"];
3
+ export type TrustEdge = (typeof TRUST_EDGES)[number];
4
+ /**
5
+ * Resolve the trust edge for a `(target_system_kind, operation)` pair.
6
+ * Returns `null` if the kind is not recognized — callers MUST treat
7
+ * this as a gap (record the kind, do not invent a trust edge).
8
+ */
9
+ export declare function classify(target_system_kind: string, operation: string): TrustEdge | null;
10
+ /** All target_system_kind values this mapping recognizes. */
11
+ export declare function knownKinds(): ReadonlySet<string>;
12
+ //# sourceMappingURL=trust_edge_mapping.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trust_edge_mapping.d.ts","sourceRoot":"","sources":["../src/trust_edge_mapping.ts"],"names":[],"mappings":"AAUA,eAAO,MAAM,eAAe,EAAG,OAAgB,CAAC;AAEhD,eAAO,MAAM,WAAW,qDAAsD,CAAC;AAC/E,MAAM,MAAM,SAAS,GAAG,CAAC,OAAO,WAAW,CAAC,CAAC,MAAM,CAAC,CAAC;AA8DrD;;;;GAIG;AACH,wBAAgB,QAAQ,CACtB,kBAAkB,EAAE,MAAM,EAC1B,SAAS,EAAE,MAAM,GAChB,SAAS,GAAG,IAAI,CAalB;AAED,6DAA6D;AAC7D,wBAAgB,UAAU,IAAI,WAAW,CAAC,MAAM,CAAC,CAEhD"}