usertrust 1.5.0 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (115) hide show
  1. package/README.md +17 -1
  2. package/dist/anomaly/detector.js.map +1 -1
  3. package/dist/anomaly/index.d.ts +2 -2
  4. package/dist/anomaly/index.d.ts.map +1 -1
  5. package/dist/anomaly/index.js +1 -1
  6. package/dist/anomaly/index.js.map +1 -1
  7. package/dist/audit/anchor-doctor.d.ts +42 -0
  8. package/dist/audit/anchor-doctor.d.ts.map +1 -0
  9. package/dist/audit/anchor-doctor.js +285 -0
  10. package/dist/audit/anchor-doctor.js.map +1 -0
  11. package/dist/audit/anchor-verify.d.ts +229 -0
  12. package/dist/audit/anchor-verify.d.ts.map +1 -0
  13. package/dist/audit/anchor-verify.js +809 -0
  14. package/dist/audit/anchor-verify.js.map +1 -0
  15. package/dist/audit/anchor.d.ts +177 -0
  16. package/dist/audit/anchor.d.ts.map +1 -0
  17. package/dist/audit/anchor.js +922 -0
  18. package/dist/audit/anchor.js.map +1 -0
  19. package/dist/audit/canonical.js +1 -1
  20. package/dist/audit/canonical.js.map +1 -1
  21. package/dist/audit/chain.d.ts.map +1 -1
  22. package/dist/audit/chain.js +21 -7
  23. package/dist/audit/chain.js.map +1 -1
  24. package/dist/audit/read.d.ts +19 -0
  25. package/dist/audit/read.d.ts.map +1 -0
  26. package/dist/audit/read.js +94 -0
  27. package/dist/audit/read.js.map +1 -0
  28. package/dist/audit/rekor-verify.d.ts +116 -0
  29. package/dist/audit/rekor-verify.d.ts.map +1 -0
  30. package/dist/audit/rekor-verify.js +533 -0
  31. package/dist/audit/rekor-verify.js.map +1 -0
  32. package/dist/audit/rekor.d.ts +71 -0
  33. package/dist/audit/rekor.d.ts.map +1 -0
  34. package/dist/audit/rekor.js +556 -0
  35. package/dist/audit/rekor.js.map +1 -0
  36. package/dist/audit/rotation.js +1 -1
  37. package/dist/audit/rotation.js.map +1 -1
  38. package/dist/audit/sigv4.d.ts +44 -0
  39. package/dist/audit/sigv4.d.ts.map +1 -0
  40. package/dist/audit/sigv4.js +134 -0
  41. package/dist/audit/sigv4.js.map +1 -0
  42. package/dist/audit/verify.d.ts +78 -0
  43. package/dist/audit/verify.d.ts.map +1 -1
  44. package/dist/audit/verify.js +195 -1
  45. package/dist/audit/verify.js.map +1 -1
  46. package/dist/cli/anchor.d.ts +3 -0
  47. package/dist/cli/anchor.d.ts.map +1 -0
  48. package/dist/cli/anchor.js +626 -0
  49. package/dist/cli/anchor.js.map +1 -0
  50. package/dist/cli/completions.js +1 -1
  51. package/dist/cli/export.d.ts +3 -0
  52. package/dist/cli/export.d.ts.map +1 -0
  53. package/dist/cli/export.js +58 -0
  54. package/dist/cli/export.js.map +1 -0
  55. package/dist/cli/health.js.map +1 -1
  56. package/dist/cli/init.js +1 -1
  57. package/dist/cli/init.js.map +1 -1
  58. package/dist/cli/inspect.d.ts.map +1 -1
  59. package/dist/cli/inspect.js +4 -34
  60. package/dist/cli/inspect.js.map +1 -1
  61. package/dist/cli/main.d.ts +2 -2
  62. package/dist/cli/main.d.ts.map +1 -1
  63. package/dist/cli/main.js +20 -1
  64. package/dist/cli/main.js.map +1 -1
  65. package/dist/cli/pricing.js +1 -1
  66. package/dist/cli/pricing.js.map +1 -1
  67. package/dist/cli/ui.d.ts +3 -0
  68. package/dist/cli/ui.d.ts.map +1 -0
  69. package/dist/cli/ui.js +35 -0
  70. package/dist/cli/ui.js.map +1 -0
  71. package/dist/cli/verify.d.ts.map +1 -1
  72. package/dist/cli/verify.js +342 -3
  73. package/dist/cli/verify.js.map +1 -1
  74. package/dist/config.d.ts.map +1 -1
  75. package/dist/config.js.map +1 -1
  76. package/dist/detect.d.ts +37 -15
  77. package/dist/detect.d.ts.map +1 -1
  78. package/dist/detect.js +17 -6
  79. package/dist/detect.js.map +1 -1
  80. package/dist/export/markdown.d.ts +12 -0
  81. package/dist/export/markdown.d.ts.map +1 -0
  82. package/dist/export/markdown.js +142 -0
  83. package/dist/export/markdown.js.map +1 -0
  84. package/dist/govern.d.ts +60 -3
  85. package/dist/govern.d.ts.map +1 -1
  86. package/dist/govern.js +842 -229
  87. package/dist/govern.js.map +1 -1
  88. package/dist/headless.d.ts.map +1 -1
  89. package/dist/headless.js +4 -4
  90. package/dist/headless.js.map +1 -1
  91. package/dist/index.d.ts +33 -26
  92. package/dist/index.d.ts.map +1 -1
  93. package/dist/index.js +30 -25
  94. package/dist/index.js.map +1 -1
  95. package/dist/ledger/client.d.ts.map +1 -1
  96. package/dist/ledger/client.js +57 -46
  97. package/dist/ledger/client.js.map +1 -1
  98. package/dist/ledger/engine.d.ts.map +1 -1
  99. package/dist/ledger/engine.js +22 -13
  100. package/dist/ledger/engine.js.map +1 -1
  101. package/dist/shared/types.d.ts +114 -475
  102. package/dist/shared/types.d.ts.map +1 -1
  103. package/dist/shared/types.js +13 -13
  104. package/dist/shared/types.js.map +1 -1
  105. package/dist/snapshot/checkpoint.d.ts.map +1 -1
  106. package/dist/snapshot/checkpoint.js +20 -2
  107. package/dist/snapshot/checkpoint.js.map +1 -1
  108. package/dist/streaming.d.ts +9 -4
  109. package/dist/streaming.d.ts.map +1 -1
  110. package/dist/streaming.js +27 -0
  111. package/dist/streaming.js.map +1 -1
  112. package/dist/supply-chain/sign.d.ts.map +1 -1
  113. package/dist/supply-chain/sign.js +3 -0
  114. package/dist/supply-chain/sign.js.map +1 -1
  115. package/package.json +6 -4
package/README.md CHANGED
@@ -112,7 +112,8 @@ All commands support `--json` for machine-readable output.
112
112
  usertrust init # Create .usertrust/ vault
113
113
  usertrust inspect # Vault bank statement
114
114
  usertrust health # Entropy diagnostics (6 signals, 0-100 score)
115
- usertrust verify # Verify audit chain integrity
115
+ usertrust verify # Verify audit chain integrity (+ external anchors)
116
+ usertrust anchor # External anchoring: init|now|status|doctor|export|export-bundle|rotate|resume
116
117
  usertrust snapshot # Checkpoint/restore vault state
117
118
  usertrust tb # TigerBeetle process management
118
119
  usertrust completions # Shell completions (bash, zsh, fish)
@@ -189,6 +190,8 @@ const config = defineConfig({
189
190
 
190
191
  **Merkle proofs (RFC 6962)** — Inclusion and consistency proofs for public verifiability. Any third party can verify a specific event existed in the chain.
191
192
 
193
+ **External anchoring** — Ed25519-signed chain-head checkpoints pushed to an append-only store the vault operator cannot rewrite (S3 Object Lock, protected git branch, SIEM). Even a fully re-hashed, internally-consistent rewrite fails verification against the externally-held root. Ships a native SigV4 S3 sink (no AWS SDK), an experimental [Rekor](https://docs.sigstore.dev/logging/overview/) transparency-log witness that publishes digests only, `anchor doctor` to probe whether the writer identity can actually delete or overwrite in the store, and `anchor export-bundle` to hand an auditor the records and receipts in one file. See the [anchoring guide](https://github.com/usertools-ai/usertrust/blob/master/docs/anchoring.md).
194
+
192
195
  **Policy engine** — 12 field operators (`eq`, `gt`, `in`, `regex`, etc.) with soft/hard enforcement. Block specific models, cap costs, require approvals.
193
196
 
194
197
  **PII detection** — Luhn-validated credit card numbers, SSN patterns, email addresses, phone numbers, IPv4 addresses. Block or warn before data leaves your network.
@@ -255,6 +258,19 @@ All hashes: valid (847/847)
255
258
 
256
259
  The verify package has zero runtime dependencies. It reads JSONL, recomputes SHA-256 hashes, and checks the chain. Anyone can verify a vault without trusting the usertrust SDK.
257
260
 
261
+ With [external anchoring](https://github.com/usertools-ai/usertrust/blob/master/docs/anchoring.md) enabled, verification goes further: the auditor fetches signed checkpoints from an append-only store the operator cannot rewrite and pins the public key out-of-band — so even a fully re-hashed rewrite of the vault fails:
262
+
263
+ ```bash
264
+ usertrust anchor init # once: mint identity, pin the key
265
+ usertrust anchor now --sink-file /mnt/worm/anchors.jsonl # from cron/CI, or in-process
266
+
267
+ # or publish straight to S3, after checking the store really refuses deletes
268
+ usertrust anchor doctor --sink-s3 bucket=audit-anchors,region=us-east-1
269
+ usertrust anchor now --sink-s3 bucket=audit-anchors,region=us-east-1
270
+
271
+ npx usertrust-verify .usertrust --anchors anchors.jsonl --pubkey root.pem --require-external-anchor
272
+ ```
273
+
258
274
  ## License
259
275
 
260
276
  Apache 2.0
@@ -1 +1 @@
1
- {"version":3,"file":"detector.js","sourceRoot":"","sources":["../../src/anomaly/detector.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"detector.js","sourceRoot":"","sources":["../../src/anomaly/detector.ts"],"names":[],"mappings":"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"}
@@ -1,8 +1,8 @@
1
1
  /**
2
2
  * anomaly/index.ts — Public exports for streaming anomaly governance.
3
3
  */
4
- export { createAnomalyDetector, resolveAnomalyConfig } from "./detector.js";
4
+ export { AnomalyError } from "../shared/errors.js";
5
5
  export type { AnomalyDetector } from "./detector.js";
6
+ export { createAnomalyDetector, resolveAnomalyConfig } from "./detector.js";
6
7
  export type { AnomalyChunkEvent, AnomalyConfig, AnomalyDetectorOptions, AnomalyDetectorState, AnomalyEvent, AnomalyInjectionEvent, AnomalyKind, AnomalyVerdict, InjectionCascadeConfig, ResolvedAnomalyConfig, SpendVelocityConfig, TokenRateConfig, } from "./types.js";
7
- export { AnomalyError } from "../shared/errors.js";
8
8
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/anomaly/index.ts"],"names":[],"mappings":"AAGA;;GAEG;AAEH,OAAO,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,MAAM,eAAe,CAAC;AAC5E,YAAY,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AACrD,YAAY,EACX,iBAAiB,EACjB,aAAa,EACb,sBAAsB,EACtB,oBAAoB,EACpB,YAAY,EACZ,qBAAqB,EACrB,WAAW,EACX,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,mBAAmB,EACnB,eAAe,GACf,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/anomaly/index.ts"],"names":[],"mappings":"AAGA;;GAEG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,YAAY,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AACrD,OAAO,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,MAAM,eAAe,CAAC;AAC5E,YAAY,EACX,iBAAiB,EACjB,aAAa,EACb,sBAAsB,EACtB,oBAAoB,EACpB,YAAY,EACZ,qBAAqB,EACrB,WAAW,EACX,cAAc,EACd,sBAAsB,EACtB,qBAAqB,EACrB,mBAAmB,EACnB,eAAe,GACf,MAAM,YAAY,CAAC"}
@@ -3,6 +3,6 @@
3
3
  /**
4
4
  * anomaly/index.ts — Public exports for streaming anomaly governance.
5
5
  */
6
- export { createAnomalyDetector, resolveAnomalyConfig } from "./detector.js";
7
6
  export { AnomalyError } from "../shared/errors.js";
7
+ export { createAnomalyDetector, resolveAnomalyConfig } from "./detector.js";
8
8
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/anomaly/index.ts"],"names":[],"mappings":"AAAA,sCAAsC;AACtC,iCAAiC;AAEjC;;GAEG;AAEH,OAAO,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,MAAM,eAAe,CAAC;AAgB5E,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/anomaly/index.ts"],"names":[],"mappings":"AAAA,sCAAsC;AACtC,iCAAiC;AAEjC;;GAEG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAEnD,OAAO,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,MAAM,eAAe,CAAC"}
@@ -0,0 +1,42 @@
1
+ export interface DoctorCheck {
2
+ name: string;
3
+ status: "pass" | "fail" | "info";
4
+ detail: string;
5
+ }
6
+ export interface DoctorReport {
7
+ sink: string;
8
+ checks: DoctorCheck[];
9
+ failed: boolean;
10
+ }
11
+ /**
12
+ * Injectable HTTP transport — the probe's only impure edge, so tests script
13
+ * store responses instead of reaching the network. Response `headers` are
14
+ * optional because only the S3 versioning probe reads one.
15
+ */
16
+ export type HttpTransport = (opts: {
17
+ method: string;
18
+ url: string;
19
+ headers: Record<string, string>;
20
+ body: Buffer;
21
+ }) => Promise<{
22
+ status: number;
23
+ body: string;
24
+ headers?: Record<string, string>;
25
+ }>;
26
+ export interface S3ProbeConfig {
27
+ bucket: string;
28
+ region: string;
29
+ prefix?: string;
30
+ endpoint?: string;
31
+ }
32
+ /**
33
+ * Probe the directory holding a file sink. The probe object is created next to
34
+ * the store file (same directory, hence same permissions) and removed again.
35
+ */
36
+ export declare function doctorFileSink(sinkPath: string): DoctorReport;
37
+ /**
38
+ * Probe an S3-compatible store: write a probe object, then attempt the two
39
+ * operations an append-only store must refuse against that same key.
40
+ */
41
+ export declare function doctorS3Sink(cfg: S3ProbeConfig, transport?: HttpTransport): Promise<DoctorReport>;
42
+ //# sourceMappingURL=anchor-doctor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"anchor-doctor.d.ts","sourceRoot":"","sources":["../../src/audit/anchor-doctor.ts"],"names":[],"mappings":"AAkCA,MAAM,WAAW,WAAW;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,MAAM,CAAC;IACjC,MAAM,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,YAAY;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,WAAW,EAAE,CAAC;IACtB,MAAM,EAAE,OAAO,CAAC;CAChB;AAED;;;;GAIG;AACH,MAAM,MAAM,aAAa,GAAG,CAAC,IAAI,EAAE;IAClC,MAAM,EAAE,MAAM,CAAC;IACf,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAChC,IAAI,EAAE,MAAM,CAAC;CACb,KAAK,OAAO,CAAC;IAAE,MAAM,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAA;CAAE,CAAC,CAAC;AAElF,MAAM,WAAW,aAAa;IAC7B,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC;CAClB;AA2CD;;;GAGG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,YAAY,CAmD7D;AA6BD;;;GAGG;AACH,wBAAsB,YAAY,CACjC,GAAG,EAAE,aAAa,EAClB,SAAS,GAAE,aAA8B,GACvC,OAAO,CAAC,YAAY,CAAC,CAsCvB"}
@@ -0,0 +1,285 @@
1
+ // SPDX-License-Identifier: Apache-2.0
2
+ // Copyright 2026 Usertools, Inc.
3
+ /**
4
+ * `anchor doctor` — append-only store PERMISSION PROBES.
5
+ *
6
+ * What this module establishes is narrow and worth stating precisely: it writes
7
+ * a throwaway probe object to the store and reports whether THIS identity, with
8
+ * the credentials in THIS environment, could delete or overwrite that object
9
+ * RIGHT NOW. It does not prove the store is append-only. A store can deny these
10
+ * operations today and allow them tomorrow, deny them for this identity and
11
+ * allow them for an admin one, or accept an overwrite as a new object version.
12
+ * Immutability comes from the store's own configuration (S3 Object Lock
13
+ * retention, POSIX directory permissions, an appliance's WORM mode) — the
14
+ * doctor only tells an operator whether their configuration is doing anything
15
+ * at all, which is the failure mode worth catching before an audit.
16
+ *
17
+ * The two probes are independent on purpose: on POSIX, deletion is governed by
18
+ * write permission on the DIRECTORY while in-place truncation is governed by
19
+ * permission on the FILE, so a store can deny one and allow the other.
20
+ *
21
+ * The S3 probe leaves its probe object behind whenever the store denies
22
+ * deletion — that is the store working as intended, not a leak, and the probe
23
+ * key is named in every check detail so it can be reconciled or lifecycled.
24
+ *
25
+ * Never in the output: credentials, the `authorization` header, or the session
26
+ * token — a diagnostic that gets pasted into an issue tracker must be safe to
27
+ * paste (plan delta D6).
28
+ */
29
+ import { closeSync, openSync, unlinkSync, writeSync } from "node:fs";
30
+ import { dirname, join } from "node:path";
31
+ import { sigV4Headers } from "./sigv4.js";
32
+ const PROBE_BODY = Buffer.from(`${JSON.stringify({ probe: "usertrust-anchor-doctor", note: "safe to delete" })}\n`, "utf8");
33
+ // ── Report helpers ──
34
+ const pass = (name, detail) => ({ name, status: "pass", detail });
35
+ const fail = (name, detail) => ({ name, status: "fail", detail });
36
+ const info = (name, detail) => ({ name, status: "info", detail });
37
+ function report(sink, checks) {
38
+ return { sink, checks, failed: checks.some((c) => c.status === "fail") };
39
+ }
40
+ /**
41
+ * Untrusted text (store error bodies, transport error messages) on its way into
42
+ * a check detail. Anything that could carry a signed header is dropped to the
43
+ * end of its line rather than partially masked — a diagnostic is worth less
44
+ * than a credential.
45
+ */
46
+ function redact(text) {
47
+ const scrubbed = text
48
+ .replace(/authorization[^\n]*/gi, "[redacted]")
49
+ .replace(/x-amz-security-token[^\n]*/gi, "[redacted]")
50
+ .replace(/AWS4-HMAC-SHA256[^\n]*/g, "[redacted]")
51
+ .replace(/Credential=[^\s,]*/g, "[redacted]")
52
+ .replace(/Signature=[^\s,]*/g, "[redacted]")
53
+ .replace(/\s+/g, " ")
54
+ .trim();
55
+ return scrubbed.length > 120 ? `${scrubbed.slice(0, 120)}…` : scrubbed;
56
+ }
57
+ const messageOf = (err) => redact(err instanceof Error ? err.message : String(err));
58
+ const errnoOf = (err) => typeof err.code === "string" ? err.code : "unknown";
59
+ // ── File sink ──
60
+ /**
61
+ * Probe the directory holding a file sink. The probe object is created next to
62
+ * the store file (same directory, hence same permissions) and removed again.
63
+ */
64
+ export function doctorFileSink(sinkPath) {
65
+ const sink = `file:${sinkPath}`;
66
+ const dir = dirname(sinkPath);
67
+ // PID-scoped so concurrent doctors never probe each other's object; opened
68
+ // with "w" so a stale probe from a crashed run is reused, not fatal.
69
+ const probe = join(dir, `.doctor-probe-${process.pid}`);
70
+ const created = writeProbe(probe);
71
+ if (created !== null) {
72
+ return report(sink, [
73
+ info("probe", `cannot probe: this identity could not create a probe object in ${dir} (${created}) — ` +
74
+ "the store's delete and overwrite permissions were not exercised"),
75
+ ]);
76
+ }
77
+ const checks = [];
78
+ let deleted = false;
79
+ try {
80
+ unlinkSync(probe);
81
+ deleted = true;
82
+ checks.push(fail("delete-denied", `this identity could delete a probe object at ${probe} right now`));
83
+ }
84
+ catch (err) {
85
+ checks.push(pass("delete-denied", `this identity could not delete a probe object at ${probe} right now (${errnoOf(err)})`));
86
+ }
87
+ // The delete probe consumed the object when it succeeded; the overwrite
88
+ // probe needs one to truncate.
89
+ const recreated = deleted ? writeProbe(probe) : null;
90
+ if (recreated !== null) {
91
+ checks.push(info("overwrite-denied", `cannot probe overwrite: ${recreated}`));
92
+ return report(sink, checks);
93
+ }
94
+ checks.push(overwriteProbe(probe));
95
+ try {
96
+ unlinkSync(probe);
97
+ }
98
+ catch {
99
+ // Best effort: a store that refuses the delete is the passing case, and
100
+ // the probe object is named in the check detail either way.
101
+ }
102
+ return report(sink, checks);
103
+ }
104
+ /** Creates or truncates the probe object; returns an errno on failure, else null. */
105
+ function writeProbe(probe) {
106
+ try {
107
+ const fd = openSync(probe, "w", 0o600);
108
+ try {
109
+ writeSync(fd, PROBE_BODY);
110
+ }
111
+ finally {
112
+ closeSync(fd);
113
+ }
114
+ return null;
115
+ }
116
+ catch (err) {
117
+ return errnoOf(err);
118
+ }
119
+ }
120
+ function overwriteProbe(probe) {
121
+ const errno = writeProbe(probe);
122
+ return errno === null
123
+ ? fail("overwrite-denied", `this identity could overwrite a probe object at ${probe} right now`)
124
+ : pass("overwrite-denied", `this identity could not overwrite a probe object at ${probe} right now (${errno})`);
125
+ }
126
+ // ── S3 sink ──
127
+ /**
128
+ * Probe an S3-compatible store: write a probe object, then attempt the two
129
+ * operations an append-only store must refuse against that same key.
130
+ */
131
+ export async function doctorS3Sink(cfg, transport = httpsTransport) {
132
+ const prefix = (cfg.prefix ?? "anchors").replace(/^\/+|\/+$/g, "");
133
+ const sink = `s3:${cfg.bucket}/${prefix}`;
134
+ const creds = credentialsFromEnv();
135
+ if (creds === null) {
136
+ return report(sink, [
137
+ info("probe", "cannot probe: AWS credentials not found in the environment " +
138
+ "(AWS_ACCESS_KEY_ID / AWS_SECRET_ACCESS_KEY)"),
139
+ ]);
140
+ }
141
+ const target = probeTarget(cfg, prefix);
142
+ const loc = `s3://${cfg.bucket}/${target.key}`;
143
+ const send = (method, payload) => s3Request(transport, target, cfg.region, method, payload, creds);
144
+ const put = await attempt(() => send("PUT", PROBE_BODY));
145
+ if (put.error !== null) {
146
+ return report(sink, [info("probe", `cannot probe: writing ${loc} failed — ${put.error}`)]);
147
+ }
148
+ if (!is2xx(put.status)) {
149
+ return report(sink, [
150
+ info("probe", `cannot probe: writing ${loc} returned HTTP ${put.status}${snippet(put.body)} — ` +
151
+ "the store's delete and overwrite permissions were not exercised"),
152
+ ]);
153
+ }
154
+ return report(sink, [
155
+ verdict("delete-denied", "delete", loc, await attempt(() => send("DELETE", Buffer.alloc(0)))),
156
+ verdict("overwrite-denied", "overwrite", loc, await attempt(() => send("PUT", PROBE_BODY))),
157
+ ]);
158
+ }
159
+ async function attempt(run) {
160
+ try {
161
+ const res = await run();
162
+ const headers = res.headers ?? {};
163
+ const versionId = Object.entries(headers).find(([k]) => k.toLowerCase() === "x-amz-version-id")?.[1] ?? null;
164
+ return { status: res.status, body: res.body, versionId, error: null };
165
+ }
166
+ catch (err) {
167
+ return { status: 0, body: "", versionId: null, error: messageOf(err) };
168
+ }
169
+ }
170
+ /**
171
+ * Turn one store response into a verdict. 403 is the shape a store takes when
172
+ * its policy refuses; a 2xx that carries `x-amz-version-id` is neither a
173
+ * refusal nor a true overwrite, so it reports as info rather than a verdict.
174
+ */
175
+ function verdict(name, op, loc, res) {
176
+ if (res.error !== null) {
177
+ return info(name, `cannot probe ${op}: ${loc} — ${res.error}`);
178
+ }
179
+ if (res.status === 403) {
180
+ return pass(name, `this identity could not ${op} a probe object at ${loc} right now (HTTP 403)`);
181
+ }
182
+ if (!is2xx(res.status)) {
183
+ return info(name, `inconclusive: ${op} of ${loc} returned HTTP ${res.status}${snippet(res.body)}`);
184
+ }
185
+ if (op === "overwrite" && res.versionId !== null) {
186
+ return info(name, `this identity could write a new version of a probe object at ${loc} right now ` +
187
+ `(HTTP ${res.status}, x-amz-version-id) — a new version does not remove the previous ` +
188
+ "one; confirm Object Lock retention denies deletion of individual versions");
189
+ }
190
+ return fail(name, `this identity could ${op} a probe object at ${loc} right now (HTTP ${res.status})`);
191
+ }
192
+ const is2xx = (status) => status >= 200 && status < 300;
193
+ const snippet = (body) => (body === "" ? "" : `: ${redact(body)}`);
194
+ function credentialsFromEnv() {
195
+ const accessKeyId = process.env.AWS_ACCESS_KEY_ID;
196
+ const secretAccessKey = process.env.AWS_SECRET_ACCESS_KEY;
197
+ if (!accessKeyId || !secretAccessKey)
198
+ return null;
199
+ const sessionToken = process.env.AWS_SESSION_TOKEN;
200
+ return { accessKeyId, secretAccessKey, ...(sessionToken ? { sessionToken } : {}) };
201
+ }
202
+ /** Virtual-host addressing by default; path-style when an endpoint is configured. */
203
+ function probeTarget(cfg, prefix) {
204
+ const key = `${prefix === "" ? "" : `${prefix}/`}doctor-probe/${process.pid}-${amzDate()}.json`;
205
+ const encoded = key.split("/").map(encodeURIComponent).join("/");
206
+ if (cfg.endpoint !== undefined) {
207
+ const base = parseEndpoint(cfg.endpoint);
208
+ const path = `/${encodeURIComponent(cfg.bucket)}/${encoded}`;
209
+ return { host: base.host, path, url: `${base.protocol}//${base.host}${path}`, key };
210
+ }
211
+ const host = `${cfg.bucket}.s3.${cfg.region}.amazonaws.com`;
212
+ return { host, path: `/${encoded}`, url: `https://${host}/${encoded}`, key };
213
+ }
214
+ /**
215
+ * Endpoint for an S3-compatible store, under the SAME rule as the sink
216
+ * (rekor.ts / s3-sink): plaintext is refused off-loopback. The doctor's probes
217
+ * are SigV4-signed like any other request, so an http endpoint on the network
218
+ * would put the credential-bearing headers on the wire — and a diagnostic
219
+ * command is exactly where an operator would paste an attacker-suggested URL.
220
+ * Loopback stays allowed for dev MinIO/LocalStack.
221
+ */
222
+ function parseEndpoint(endpoint) {
223
+ let url;
224
+ try {
225
+ url = new URL(endpoint);
226
+ }
227
+ catch {
228
+ throw new Error(`s3 doctor: endpoint must include a scheme, got "${endpoint.slice(0, 60)}"`);
229
+ }
230
+ const loopback = url.hostname === "localhost" || url.hostname === "127.0.0.1";
231
+ if (url.protocol !== "https:" && !(url.protocol === "http:" && loopback)) {
232
+ throw new Error(`s3 doctor: endpoint must be https (http is allowed only for localhost/127.0.0.1), got "${url.protocol}//${url.host}"`);
233
+ }
234
+ return url;
235
+ }
236
+ /** `YYYYMMDDTHHMMSSZ` — also the probe key's uniqueness across runs. */
237
+ function amzDate() {
238
+ return `${new Date().toISOString().replace(/[-:]/g, "").slice(0, 15)}Z`;
239
+ }
240
+ function s3Request(transport, target, region, method, payload, creds) {
241
+ const extra = payload.length > 0 ? { "content-type": "application/json" } : {};
242
+ const signed = sigV4Headers({
243
+ method,
244
+ host: target.host,
245
+ path: target.path,
246
+ headers: extra,
247
+ payload,
248
+ region,
249
+ service: "s3",
250
+ amzDate: amzDate(),
251
+ }, creds);
252
+ // sigV4Headers signs caller headers but returns only its own — the caller
253
+ // must send both, or the signature covers headers that never arrive.
254
+ return transport({ method, url: target.url, headers: { ...extra, ...signed }, body: payload });
255
+ }
256
+ /** Default transport. `http://` endpoints (dev MinIO) require an injected one. */
257
+ async function httpsTransport(opts) {
258
+ const { request } = await import("node:https");
259
+ return new Promise((resolve, reject) => {
260
+ const req = request(opts.url, {
261
+ method: opts.method,
262
+ headers: { ...opts.headers, "content-length": String(opts.body.length) },
263
+ timeout: 15_000,
264
+ }, (res) => {
265
+ const chunks = [];
266
+ res.on("data", (c) => chunks.push(c));
267
+ res.on("end", () => {
268
+ const headers = {};
269
+ for (const [name, value] of Object.entries(res.headers)) {
270
+ if (typeof value === "string")
271
+ headers[name] = value;
272
+ }
273
+ resolve({
274
+ status: res.statusCode ?? 0,
275
+ body: Buffer.concat(chunks).toString("utf8").slice(0, 4096),
276
+ headers,
277
+ });
278
+ });
279
+ });
280
+ req.on("timeout", () => req.destroy(new Error("s3 doctor: request timeout")));
281
+ req.on("error", reject);
282
+ req.end(opts.body);
283
+ });
284
+ }
285
+ //# sourceMappingURL=anchor-doctor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"anchor-doctor.js","sourceRoot":"","sources":["../../src/audit/anchor-doctor.ts"],"names":[],"mappings":"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"}