@tenova/swt3-ai 0.5.1 → 0.5.2
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 +192 -8
- package/dist/buffer.d.ts +7 -1
- package/dist/buffer.d.ts.map +1 -1
- package/dist/buffer.js +38 -3
- package/dist/buffer.js.map +1 -1
- package/dist/cli.d.ts +13 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +202 -0
- package/dist/cli.js.map +1 -0
- package/dist/config.d.ts +18 -5
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +346 -42
- package/dist/config.js.map +1 -1
- package/dist/demo.d.ts +1 -1
- package/dist/demo.d.ts.map +1 -1
- package/dist/demo.js +88 -4
- package/dist/demo.js.map +1 -1
- package/dist/doctor.d.ts +20 -0
- package/dist/doctor.d.ts.map +1 -0
- package/dist/doctor.js +357 -0
- package/dist/doctor.js.map +1 -0
- package/dist/environment.d.ts +34 -0
- package/dist/environment.d.ts.map +1 -0
- package/dist/environment.js +99 -0
- package/dist/environment.js.map +1 -0
- package/dist/exporters/chain-monitor.d.ts +55 -0
- package/dist/exporters/chain-monitor.d.ts.map +1 -0
- package/dist/exporters/chain-monitor.js +172 -0
- package/dist/exporters/chain-monitor.js.map +1 -0
- package/dist/hardware.d.ts +96 -0
- package/dist/hardware.d.ts.map +1 -0
- package/dist/hardware.js +265 -0
- package/dist/hardware.js.map +1 -0
- package/dist/index.d.ts +19 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +10 -2
- package/dist/index.js.map +1 -1
- package/dist/merkle.d.ts +107 -0
- package/dist/merkle.d.ts.map +1 -0
- package/dist/merkle.js +226 -0
- package/dist/merkle.js.map +1 -0
- package/dist/schema.d.ts +18 -0
- package/dist/schema.d.ts.map +1 -0
- package/dist/schema.js +255 -0
- package/dist/schema.js.map +1 -0
- package/dist/trust.d.ts +100 -0
- package/dist/trust.d.ts.map +1 -0
- package/dist/trust.js +222 -0
- package/dist/trust.js.map +1 -0
- package/dist/types.d.ts +167 -11
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js +42 -1
- package/dist/types.js.map +1 -1
- package/dist/wal.d.ts +69 -0
- package/dist/wal.d.ts.map +1 -0
- package/dist/wal.js +223 -0
- package/dist/wal.js.map +1 -0
- package/dist/witness.d.ts +293 -1
- package/dist/witness.d.ts.map +1 -1
- package/dist/witness.js +1234 -5
- package/dist/witness.js.map +1 -1
- package/package.json +4 -2
- package/templates/eu-ai-act-high-risk.yaml +56 -0
- package/templates/granite-sovereign.yaml +55 -0
- package/templates/minimal.yaml +38 -0
- package/templates/mythos-defense.yaml +65 -0
- package/templates/nist-ai-rmf.yaml +47 -0
- package/templates/owasp-agentic-top10.yaml +50 -0
package/README.md
CHANGED
|
@@ -3,6 +3,7 @@ Witness your AI. Prove it followed the rules. Cryptographic accountability for e
|
|
|
3
3
|
[](https://www.npmjs.com/package/@tenova/swt3-ai)
|
|
4
4
|
[](https://www.npmjs.com/package/@tenova/swt3-ai)
|
|
5
5
|
[](https://github.com/tenova-labs/swt3-ai/blob/main/LICENSE)
|
|
6
|
+
[](https://www.npmjs.com/package/@tenova/swt3-mcp)
|
|
6
7
|
|
|
7
8
|
# @tenova/swt3-ai
|
|
8
9
|
|
|
@@ -12,6 +13,72 @@ Works with OpenAI, Anthropic, AWS Bedrock, Vercel AI SDK, and any OpenAI-compati
|
|
|
12
13
|
|
|
13
14
|
GPAI transparency obligations are enforceable now. EU AI Act high-risk enforcement begins **December 2, 2027**. This SDK gives you the evidence chain.
|
|
14
15
|
|
|
16
|
+
## MCP Server -- Official Registry
|
|
17
|
+
|
|
18
|
+
`@tenova/swt3-mcp` is listed on the official Model Context Protocol Registry as `io.tenova/swt3-witness`. Zero-config compliance governance for Claude Code, Cursor, Windsurf, and any MCP-compatible host.
|
|
19
|
+
|
|
20
|
+
```json
|
|
21
|
+
{
|
|
22
|
+
"mcpServers": {
|
|
23
|
+
"swt3-witness": {
|
|
24
|
+
"command": "npx",
|
|
25
|
+
"args": ["@tenova/swt3-mcp"]
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Every tool call your agent makes is witnessed, Merkle-accumulated, and trust-evaluated. No code changes required. [Quick Start](https://www.npmjs.com/package/@tenova/swt3-mcp)
|
|
32
|
+
|
|
33
|
+
## Secure Agent-to-Agent Communication
|
|
34
|
+
|
|
35
|
+
The SWT3 Trust Mesh enables mutual cryptographic verification between AI agents before they exchange data, invoke tools, or share context. When you adopt SWT3, every partner, vendor, and downstream agent that wants to interact with yours must adopt it too. Compliance becomes the connection protocol. Every agent in the mesh strengthens the network.
|
|
36
|
+
|
|
37
|
+
**You run Agent A. Your partner runs Agent B. Both install @tenova/swt3-ai:**
|
|
38
|
+
|
|
39
|
+
```typescript
|
|
40
|
+
// === Your side (Agent A) ===
|
|
41
|
+
const witnessA = new Witness({
|
|
42
|
+
endpoint: "...", apiKey: "axm_...", tenantId: "YOUR_TENANT",
|
|
43
|
+
agentId: "agent-alpha", signingKey: "swt3_sk_your_key",
|
|
44
|
+
});
|
|
45
|
+
witnessA.trustRegistry.trustTenant("PARTNER_B_TENANT");
|
|
46
|
+
witnessA.trustRegistry.registerSigningKey("agent-beta", process.env.PARTNER_B_KEY!);
|
|
47
|
+
|
|
48
|
+
// === Partner's side (Agent B) ===
|
|
49
|
+
const witnessB = new Witness({
|
|
50
|
+
endpoint: "...", apiKey: "axm_...", tenantId: "PARTNER_B_TENANT",
|
|
51
|
+
agentId: "agent-beta", signingKey: "swt3_sk_partner_key",
|
|
52
|
+
});
|
|
53
|
+
witnessB.trustRegistry.trustTenant("YOUR_TENANT");
|
|
54
|
+
witnessB.trustRegistry.registerSigningKey("agent-alpha", process.env.YOUR_KEY!);
|
|
55
|
+
|
|
56
|
+
// === Handshake (both directions) ===
|
|
57
|
+
const credA = witnessA.presentCredential();
|
|
58
|
+
const resultB = witnessB.verifyTrust(credA); // B verifies A
|
|
59
|
+
if (resultB.granted) {
|
|
60
|
+
const credB = witnessB.presentCredential();
|
|
61
|
+
const resultA = witnessA.verifyTrust(credB); // A verifies B
|
|
62
|
+
if (resultA.granted) {
|
|
63
|
+
// Bidirectional trust established. Exchange data.
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
```
|
|
67
|
+
|
|
68
|
+
Configure trust boundaries declaratively in `.swt3.yaml`:
|
|
69
|
+
|
|
70
|
+
```yaml
|
|
71
|
+
trust_mesh:
|
|
72
|
+
mode: strict
|
|
73
|
+
min_trust_level: 2
|
|
74
|
+
require_signature: true
|
|
75
|
+
freshness_window: 3600
|
|
76
|
+
trusted_tenants: ["PARTNER_B_TENANT"]
|
|
77
|
+
deny_agents: ["revoked-agent-id"]
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
All verification is local. Zero cloud overhead. No data exchanged until both agents clear the trust gate. Unsigned agents are capped at TRUST_BASIC (level 1). Add signing keys for verified trust. Add hardware attestation for sovereign trust.
|
|
81
|
+
|
|
15
82
|
## See It Work (No Account Needed)
|
|
16
83
|
|
|
17
84
|
```bash
|
|
@@ -216,6 +283,26 @@ witness.witnessQuantization("gptq", { bits: 4, groupSize: 128 });
|
|
|
216
283
|
|
|
217
284
|
Maps to: EU AI Act Art. 15(4) (resilience against modification), Art. 12(2)(b) (version logging).
|
|
218
285
|
|
|
286
|
+
## TPM Platform Attestation (AI-HW.3)
|
|
287
|
+
|
|
288
|
+
Prove host firmware integrity via TPM 2.0. Reads PCR registers 0-7 and mints a hardware root-of-trust anchor. All raw values are SHA-256 hashed before leaving the module:
|
|
289
|
+
|
|
290
|
+
```typescript
|
|
291
|
+
// Auto-detect: reads /dev/tpm0 via tpm2-tools
|
|
292
|
+
witness.witnessTPMAttestation();
|
|
293
|
+
|
|
294
|
+
// Or provide a pre-computed snapshot
|
|
295
|
+
import { queryTPM } from "@tenova/swt3-ai";
|
|
296
|
+
const snapshot = queryTPM();
|
|
297
|
+
witness.witnessTPMAttestation({ snapshot });
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
If no TPM is available (cloud VM, dev machine), returns a valid anchor with factor_a=0. No crash, no error. Graceful degradation by design.
|
|
301
|
+
|
|
302
|
+
Use case: sovereign/air-gapped deployments where you must prove the host was not tampered with. Combined with AI-HW.1 (GPU inventory), gives full hardware root-of-trust from silicon to model.
|
|
303
|
+
|
|
304
|
+
Maps to: NIST 800-53 SC-12 (cryptographic key establishment). Patent pending.
|
|
305
|
+
|
|
219
306
|
## Environmental Attestation (Residential and Edge AI)
|
|
220
307
|
|
|
221
308
|
Witness the physical compute environment for distributed, edge-deployed, or residential AI nodes. Proves the hardware operated within safe thermal and power bounds during inference:
|
|
@@ -363,12 +450,103 @@ witnessB.trustRegistry.registerSigningKey("agent-alpha", process.env.AGENT_A_KEY
|
|
|
363
450
|
|
|
364
451
|
**Zero-friction path:** Trust mesh works without signing keys. Agents without keys get TRUST_BASIC (level 1), which is sufficient for non-sensitive coordination. Add keys when you need verified or attested trust.
|
|
365
452
|
|
|
366
|
-
**Credential auto-population:** `presentCredential()` automatically includes which procedures the agent has witnessed and whether hardware attestation (AI-HW.1) has been performed. No manual tracking needed.
|
|
453
|
+
**Credential auto-population:** `presentCredential()` automatically includes which procedures the agent has witnessed and whether hardware attestation (AI-HW.1 or AI-HW.3) has been performed. No manual tracking needed.
|
|
367
454
|
|
|
368
455
|
Every verification (pass or fail) mints AI-TRUST.1 + AI-TRUST.2 anchors. Denials produce evidence too.
|
|
369
456
|
|
|
370
457
|
Maps to: EU AI Act Art. 14 (human oversight and mutual accountability between AI systems).
|
|
371
458
|
|
|
459
|
+
## Policy-as-Code (swt3.yaml)
|
|
460
|
+
|
|
461
|
+
New in v0.5.2. Define your entire witnessing policy in a YAML file instead of passing 25+ constructor parameters:
|
|
462
|
+
|
|
463
|
+
```bash
|
|
464
|
+
npx swt3 init # interactive profile picker
|
|
465
|
+
npx swt3 init --profile eu-ai-act-high-risk --tenant ACME
|
|
466
|
+
```
|
|
467
|
+
|
|
468
|
+
This generates a `swt3.yaml` file. Then load it:
|
|
469
|
+
|
|
470
|
+
```typescript
|
|
471
|
+
const witness = Witness.fromConfig(); // auto-finds swt3.yaml
|
|
472
|
+
const witness = Witness.fromConfig("prod.yaml"); // explicit path
|
|
473
|
+
```
|
|
474
|
+
|
|
475
|
+
### File Composition (extends)
|
|
476
|
+
|
|
477
|
+
Layer configs for environment-specific overrides:
|
|
478
|
+
|
|
479
|
+
```yaml
|
|
480
|
+
# prod.yaml
|
|
481
|
+
extends: base.yaml
|
|
482
|
+
clearing_level: 2
|
|
483
|
+
signing_key_env: SWT3_SIGNING_KEY
|
|
484
|
+
```
|
|
485
|
+
|
|
486
|
+
Supports single files or chains (`extends: [base.yaml, team.yaml]`). Merge order: extends < profile < explicit config. Cycle detection and depth limit (10) built in.
|
|
487
|
+
|
|
488
|
+
### Built-in Profiles
|
|
489
|
+
|
|
490
|
+
Three profiles ship with the SDK:
|
|
491
|
+
|
|
492
|
+
| Profile | Use Case |
|
|
493
|
+
|---------|----------|
|
|
494
|
+
| `eu-ai-act-high-risk` | EU AI Act high-risk: clearing 2, signing required, jurisdiction required |
|
|
495
|
+
| `nist-ai-rmf` | NIST AI RMF: full procedure coverage, moderate policy |
|
|
496
|
+
| `minimal` | Development: clearing 0, no policy enforcement |
|
|
497
|
+
|
|
498
|
+
### Diagnostics
|
|
499
|
+
|
|
500
|
+
```bash
|
|
501
|
+
npx swt3 doctor # 8 checks: YAML, env vars, profile, extends, sections
|
|
502
|
+
npx swt3 doctor --json # machine-readable for CI/CD
|
|
503
|
+
```
|
|
504
|
+
|
|
505
|
+
### Schema Validation
|
|
506
|
+
|
|
507
|
+
Validate config files programmatically:
|
|
508
|
+
|
|
509
|
+
```typescript
|
|
510
|
+
import { validateSchema } from "@tenova/swt3-ai";
|
|
511
|
+
|
|
512
|
+
const result = validateSchema(parsedYaml);
|
|
513
|
+
if (!result.valid) {
|
|
514
|
+
console.error(result.errors);
|
|
515
|
+
}
|
|
516
|
+
```
|
|
517
|
+
|
|
518
|
+
## Merkle Accumulator (Session-Level Integrity)
|
|
519
|
+
|
|
520
|
+
New in v0.5.2. Compute Merkle roots over batches of anchors for tamper-evident session integrity:
|
|
521
|
+
|
|
522
|
+
```typescript
|
|
523
|
+
import { MerkleAccumulator, verifyMerkleProof } from "@tenova/swt3-ai";
|
|
524
|
+
|
|
525
|
+
const acc = new MerkleAccumulator({ tenantId: "ACME" });
|
|
526
|
+
|
|
527
|
+
// Accumulate fingerprints as anchors are minted
|
|
528
|
+
acc.add("abc123def456");
|
|
529
|
+
acc.add("789012345678");
|
|
530
|
+
|
|
531
|
+
// Compute session root (persisted to JSONL automatically)
|
|
532
|
+
const session = acc.flush();
|
|
533
|
+
console.log(session.root); // 64-char hex Merkle root
|
|
534
|
+
|
|
535
|
+
// Generate an inclusion proof for any fingerprint
|
|
536
|
+
const proof = acc.prove("abc123def456");
|
|
537
|
+
console.log(verifyMerkleProof("abc123def456", proof)); // true
|
|
538
|
+
```
|
|
539
|
+
|
|
540
|
+
Enable via config:
|
|
541
|
+
|
|
542
|
+
```yaml
|
|
543
|
+
merkle:
|
|
544
|
+
enabled: true
|
|
545
|
+
accumulator_interval: 0 # 0 = compute on every flush
|
|
546
|
+
```
|
|
547
|
+
|
|
548
|
+
Cross-language parity with Python SDK. Domain-separated (SWT3:LEAF: / SWT3:NODE:) to prevent second-preimage attacks.
|
|
549
|
+
|
|
372
550
|
## Gatekeeper Mode (Pre-Call Enforcement)
|
|
373
551
|
|
|
374
552
|
New in v0.3.4. Require guardrails to be active *before* the model is called, not just observed after:
|
|
@@ -456,7 +634,7 @@ Each inference produces anchors for these checks. Every check maps to a regulati
|
|
|
456
634
|
|
|
457
635
|
### EU AI Act Article Mapping
|
|
458
636
|
|
|
459
|
-
All
|
|
637
|
+
All 43 SWT3 AI witnessing procedures map to specific EU AI Act obligations:
|
|
460
638
|
|
|
461
639
|
| Procedure | EU AI Act Article | Obligation | Demo | Production |
|
|
462
640
|
|-----------|-------------------|------------|------|------------|
|
|
@@ -473,7 +651,7 @@ All 42 SWT3 AI witnessing procedures map to specific EU AI Act obligations:
|
|
|
473
651
|
| AI-EXPL.1 | Art. 13(1) | Transparency & Explainability | -| ✓ |
|
|
474
652
|
| AI-EXPL.2 | Art. 13(3b) | Confidence Calibration | -| ✓ |
|
|
475
653
|
|
|
476
|
-
The demo demonstrates 5 procedures using simulated data. All
|
|
654
|
+
The demo demonstrates 5 procedures using simulated data. All 43 are available in production with real inference data. 38 cross-language test vectors ensure fingerprint parity across Python, TypeScript, Rust, C#, and Ruby. [See live conformity →](https://sovereign.tenova.io/audit/axm_audit_demo_eu_ai_act_public)
|
|
477
655
|
|
|
478
656
|
## How Verdicts Work
|
|
479
657
|
|
|
@@ -718,15 +896,21 @@ Your prompts and responses **never leave your infrastructure**. The SDK computes
|
|
|
718
896
|
|
|
719
897
|
---
|
|
720
898
|
|
|
721
|
-
## Upgrading to v0.5.
|
|
899
|
+
## Upgrading to v0.5.2
|
|
900
|
+
|
|
901
|
+
**Policy-as-Code (new):** `swt3 init`, `swt3 doctor`, `extends:` composition, profile templates, YAML schema validator. No breaking changes.
|
|
902
|
+
|
|
903
|
+
**Merkle Accumulator (new):** `MerkleAccumulator` class for session-level integrity proofs. `merkle:` config section. No breaking changes.
|
|
904
|
+
|
|
905
|
+
**Trust Mesh (v0.5.0):** `presentCredential()` and `verifyTrust()`. No breaking changes for existing code.
|
|
722
906
|
|
|
723
|
-
**
|
|
907
|
+
**Credential signing (behavioral change):** If your Witness has a `signingKey`, credentials are now HMAC-signed automatically. Counterpart agents must register your key via `trustRegistry.registerSigningKey()` to verify the signature. Without key registration, signed credentials are denied with `signature_unverifiable`.
|
|
724
908
|
|
|
725
|
-
**
|
|
909
|
+
**TPM attestation (v0.5.2):** `witnessTPMAttestation()` for AI-HW.3. Reads PCR registers via tpm2-tools. Graceful degradation without TPM. No breaking changes.
|
|
726
910
|
|
|
727
|
-
**Environmental attestation (
|
|
911
|
+
**Environmental attestation (v0.5.0):** `witnessEnvironment()` and `witnessEnergyDraw()` for AI-ENV.1/AI-ENV.2. No breaking changes.
|
|
728
912
|
|
|
729
|
-
**MCP server:** 16 procedure keyword suggestions (was 8). No breaking changes.
|
|
913
|
+
**MCP server:** 16 procedure keyword suggestions (was 8). MCP policy section in swt3.yaml. No breaking changes.
|
|
730
914
|
|
|
731
915
|
---
|
|
732
916
|
|
package/dist/buffer.d.ts
CHANGED
|
@@ -10,6 +10,7 @@
|
|
|
10
10
|
* prevents unbounded memory growth.
|
|
11
11
|
*/
|
|
12
12
|
import type { WitnessConfig, WitnessPayload, WitnessReceipt } from "./types.js";
|
|
13
|
+
import type { WriteAheadLog } from "./wal.js";
|
|
13
14
|
export declare class WitnessBuffer {
|
|
14
15
|
private config;
|
|
15
16
|
private queue;
|
|
@@ -20,8 +21,13 @@ export declare class WitnessBuffer {
|
|
|
20
21
|
private stopped;
|
|
21
22
|
private consecutiveFailures;
|
|
22
23
|
private ctaShown;
|
|
24
|
+
private tokenAccumulator;
|
|
23
25
|
private onFlush?;
|
|
24
|
-
|
|
26
|
+
private wal;
|
|
27
|
+
private walSeqMap;
|
|
28
|
+
constructor(config: WitnessConfig, maxRetryBuffer?: number, wal?: WriteAheadLog);
|
|
29
|
+
/** Cumulative tokens accumulated since last flush (for token_budget monitoring). */
|
|
30
|
+
get tokensSinceFlush(): number;
|
|
25
31
|
/** Add a single payload to the buffer. */
|
|
26
32
|
enqueue(payload: WitnessPayload): void;
|
|
27
33
|
/** Add multiple payloads. */
|
package/dist/buffer.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"buffer.d.ts","sourceRoot":"","sources":["../src/buffer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,cAAc,EAAE,cAAc,EAAiB,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"buffer.d.ts","sourceRoot":"","sources":["../src/buffer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,cAAc,EAAE,cAAc,EAAiB,MAAM,YAAY,CAAC;AAC/F,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAI9C,qBAAa,aAAa;IACxB,OAAO,CAAC,MAAM,CAAgB;IAC9B,OAAO,CAAC,KAAK,CAAwB;IACrC,OAAO,CAAC,UAAU,CAAwB;IAC1C,OAAO,CAAC,cAAc,CAAS;IAC/B,OAAO,CAAC,WAAW,CAAwB;IAC3C,OAAO,CAAC,KAAK,CAA8C;IAC3D,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,mBAAmB,CAAK;IAChC,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,gBAAgB,CAAK;IAC7B,OAAO,CAAC,OAAO,CAAC,CAAmE;IACnF,OAAO,CAAC,GAAG,CAA8B;IACzC,OAAO,CAAC,SAAS,CAA0C;gBAE/C,MAAM,EAAE,aAAa,EAAE,cAAc,SAA2B,EAAE,GAAG,CAAC,EAAE,aAAa;IAQjG,oFAAoF;IACpF,IAAI,gBAAgB,IAAI,MAAM,CAE7B;IAED,0CAA0C;IAC1C,OAAO,CAAC,OAAO,EAAE,cAAc,GAAG,IAAI;IAuBtC,6BAA6B;IAC7B,WAAW,CAAC,QAAQ,EAAE,cAAc,EAAE,GAAG,IAAI;IAI7C,yCAAyC;IACnC,KAAK,IAAI,OAAO,CAAC,cAAc,EAAE,CAAC;IAIxC,oDAAoD;IAC9C,IAAI,IAAI,OAAO,CAAC,cAAc,EAAE,CAAC;IAgBvC,yDAAyD;IACzD,IAAI,OAAO,IAAI,MAAM,CAEpB;IAED,oDAAoD;IACpD,IAAI,eAAe,IAAI,MAAM,CAE5B;IAED,2CAA2C;IAC3C,IAAI,QAAQ,IAAI,cAAc,EAAE,CAE/B;IAED,OAAO,CAAC,UAAU;YAYJ,aAAa;YAYb,SAAS;CA8GxB"}
|
package/dist/buffer.js
CHANGED
|
@@ -20,19 +20,41 @@ export class WitnessBuffer {
|
|
|
20
20
|
stopped = false;
|
|
21
21
|
consecutiveFailures = 0;
|
|
22
22
|
ctaShown = false;
|
|
23
|
+
tokenAccumulator = 0;
|
|
23
24
|
onFlush;
|
|
24
|
-
|
|
25
|
+
wal = null;
|
|
26
|
+
walSeqMap = new Map();
|
|
27
|
+
constructor(config, maxRetryBuffer = DEFAULT_MAX_RETRY_BUFFER, wal) {
|
|
25
28
|
this.config = config;
|
|
26
29
|
this.maxRetryBuffer = maxRetryBuffer;
|
|
27
30
|
this.onFlush = config.onFlush;
|
|
31
|
+
this.wal = wal ?? null;
|
|
28
32
|
this.startTimer();
|
|
29
33
|
}
|
|
34
|
+
/** Cumulative tokens accumulated since last flush (for token_budget monitoring). */
|
|
35
|
+
get tokensSinceFlush() {
|
|
36
|
+
return this.tokenAccumulator;
|
|
37
|
+
}
|
|
30
38
|
/** Add a single payload to the buffer. */
|
|
31
39
|
enqueue(payload) {
|
|
32
40
|
if (this.stopped)
|
|
33
41
|
return;
|
|
42
|
+
// WAL: replay protection (reject duplicates) + persist to disk
|
|
43
|
+
if (this.wal) {
|
|
44
|
+
const seq = this.wal.append(payload);
|
|
45
|
+
if (seq === -1) {
|
|
46
|
+
// Duplicate fingerprint -- silently skip
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
this.walSeqMap.set(payload, seq);
|
|
50
|
+
}
|
|
51
|
+
// Track token accumulation for tokenBudget flush trigger
|
|
52
|
+
const tokens = (payload.ai_input_tokens ?? 0) + (payload.ai_output_tokens ?? 0);
|
|
53
|
+
if (tokens > 0)
|
|
54
|
+
this.tokenAccumulator += tokens;
|
|
34
55
|
this.queue.push(payload);
|
|
35
|
-
|
|
56
|
+
const tokenBudgetHit = this.config.tokenBudget != null && this.tokenAccumulator >= this.config.tokenBudget;
|
|
57
|
+
if (this.queue.length >= this.config.bufferSize || tokenBudgetHit) {
|
|
36
58
|
this.flushInternal();
|
|
37
59
|
}
|
|
38
60
|
}
|
|
@@ -89,6 +111,7 @@ export class WitnessBuffer {
|
|
|
89
111
|
const payloads = [...this.deadLetter, ...this.queue];
|
|
90
112
|
this.deadLetter = [];
|
|
91
113
|
this.queue = [];
|
|
114
|
+
this.tokenAccumulator = 0;
|
|
92
115
|
if (payloads.length === 0)
|
|
93
116
|
return [];
|
|
94
117
|
return this.sendBatch(payloads);
|
|
@@ -118,7 +141,7 @@ export class WitnessBuffer {
|
|
|
118
141
|
// Client error — don't retry, don't dead-letter
|
|
119
142
|
const text = await resp.text();
|
|
120
143
|
// Scrub any key material that might appear in error response body
|
|
121
|
-
const safe = text.replace(/(?:Bearer|Authorization|api[_-]?key|signing[_-]?key)[^\s,;"]
|
|
144
|
+
const safe = text.replace(/(?:Bearer|Authorization|api[_-]?key|signing[_-]?key)\s*[^\s,;"]{4,}/gi, "[REDACTED]");
|
|
122
145
|
console.error(`[swt3-ai] Batch flush failed (${resp.status}): ${safe.slice(0, 200)}`);
|
|
123
146
|
return [];
|
|
124
147
|
}
|
|
@@ -126,6 +149,18 @@ export class WitnessBuffer {
|
|
|
126
149
|
const receipts = result.receipts ?? [];
|
|
127
150
|
this.allReceipts.push(...receipts);
|
|
128
151
|
this.consecutiveFailures = 0;
|
|
152
|
+
// WAL: mark flushed entries
|
|
153
|
+
if (this.wal) {
|
|
154
|
+
let maxSeq = 0;
|
|
155
|
+
for (const p of payloads) {
|
|
156
|
+
const s = this.walSeqMap.get(p);
|
|
157
|
+
if (s !== undefined && s > maxSeq)
|
|
158
|
+
maxSeq = s;
|
|
159
|
+
this.walSeqMap.delete(p);
|
|
160
|
+
}
|
|
161
|
+
if (maxSeq > 0)
|
|
162
|
+
this.wal.markFlushed(maxSeq);
|
|
163
|
+
}
|
|
129
164
|
if (result.rejected > 0) {
|
|
130
165
|
console.warn(`[swt3-ai] Batch flush: ${result.accepted} accepted, ${result.rejected} rejected`);
|
|
131
166
|
}
|
package/dist/buffer.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"buffer.js","sourceRoot":"","sources":["../src/buffer.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;
|
|
1
|
+
{"version":3,"file":"buffer.js","sourceRoot":"","sources":["../src/buffer.ts"],"names":[],"mappings":"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"}
|
package/dist/cli.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* SWT3 CLI -- governance tooling for AI systems.
|
|
4
|
+
*
|
|
5
|
+
* Commands:
|
|
6
|
+
* swt3 init Interactive governance setup
|
|
7
|
+
* swt3 init --profile X Non-interactive (CI/CD friendly)
|
|
8
|
+
* swt3 demo Run the zero-friction demo
|
|
9
|
+
* swt3 doctor Diagnose config health
|
|
10
|
+
* swt3 help Show usage
|
|
11
|
+
*/
|
|
12
|
+
export declare function generateInitYaml(profile: string, tenantId: string, agentId: string): string;
|
|
13
|
+
//# sourceMappingURL=cli.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":";AACA;;;;;;;;;GASG;AA4CH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,CAoB3F"}
|
package/dist/cli.js
ADDED
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* SWT3 CLI -- governance tooling for AI systems.
|
|
4
|
+
*
|
|
5
|
+
* Commands:
|
|
6
|
+
* swt3 init Interactive governance setup
|
|
7
|
+
* swt3 init --profile X Non-interactive (CI/CD friendly)
|
|
8
|
+
* swt3 demo Run the zero-friction demo
|
|
9
|
+
* swt3 doctor Diagnose config health
|
|
10
|
+
* swt3 help Show usage
|
|
11
|
+
*/
|
|
12
|
+
import { existsSync, writeFileSync } from "node:fs";
|
|
13
|
+
import { join } from "node:path";
|
|
14
|
+
import { createInterface } from "node:readline";
|
|
15
|
+
const VERSION = "0.5.1";
|
|
16
|
+
const PROFILES = {
|
|
17
|
+
"eu-ai-act-high-risk": "EU AI Act Article 6, Annex III (strict, signing required)",
|
|
18
|
+
"granite-sovereign": "IBM Granite 4.1 + air-gap sovereign (strict, TPM required)",
|
|
19
|
+
"mythos-defense": "Exploit chain containment (strict, rate limiting, tool blocklist)",
|
|
20
|
+
"nist-ai-rmf": "NIST AI RMF + 800-53 GovCon (permissive, gradual adoption)",
|
|
21
|
+
"owasp-agentic-top10": "OWASP Agentic AI Top 10 (runtime containment, fail closed)",
|
|
22
|
+
"minimal": "Development / evaluation (no enforcement)",
|
|
23
|
+
};
|
|
24
|
+
const PROFILE_NAMES = Object.keys(PROFILES);
|
|
25
|
+
function printHelp() {
|
|
26
|
+
console.log(`
|
|
27
|
+
SWT3 CLI v${VERSION}
|
|
28
|
+
|
|
29
|
+
Usage:
|
|
30
|
+
swt3 init Interactive governance setup
|
|
31
|
+
swt3 init --profile <name> Non-interactive setup
|
|
32
|
+
swt3 init --profile <name> --tenant <id> --agent <id>
|
|
33
|
+
swt3 demo Run the zero-friction demo
|
|
34
|
+
swt3 doctor Diagnose config health
|
|
35
|
+
swt3 audit Forensic chain timeline (html or json)
|
|
36
|
+
swt3 help Show this message
|
|
37
|
+
|
|
38
|
+
Profiles:
|
|
39
|
+
${PROFILE_NAMES.map((n, i) => ` ${i + 1}. ${n.padEnd(24)} ${PROFILES[n]}`).join("\n")}
|
|
40
|
+
|
|
41
|
+
Docs: https://sovereign.tenova.io/docs/
|
|
42
|
+
`);
|
|
43
|
+
}
|
|
44
|
+
function ask(rl, question) {
|
|
45
|
+
return new Promise((resolve) => rl.question(question, resolve));
|
|
46
|
+
}
|
|
47
|
+
export function generateInitYaml(profile, tenantId, agentId) {
|
|
48
|
+
const lines = [
|
|
49
|
+
`# Generated by: swt3 init --profile ${profile}`,
|
|
50
|
+
`# Docs: https://sovereign.tenova.io/docs/`,
|
|
51
|
+
``,
|
|
52
|
+
`profile: ${profile}`,
|
|
53
|
+
``,
|
|
54
|
+
`# Required:`,
|
|
55
|
+
`tenant_id: ${tenantId || "YOUR_TENANT_ID"}`,
|
|
56
|
+
`api_key_env: SWT3_API_KEY`,
|
|
57
|
+
`agent_id: ${agentId || "your-agent-name"}`,
|
|
58
|
+
``,
|
|
59
|
+
`# Optional overrides (uncomment to customize):`,
|
|
60
|
+
`# endpoint: https://sovereign.tenova.io`,
|
|
61
|
+
`# clearing_level: 2`,
|
|
62
|
+
`# jurisdiction: US`,
|
|
63
|
+
`# signing_key_env: SWT3_SIGNING_KEY`,
|
|
64
|
+
``,
|
|
65
|
+
];
|
|
66
|
+
return lines.join("\n");
|
|
67
|
+
}
|
|
68
|
+
async function handleInit(args) {
|
|
69
|
+
const outputPath = join(process.cwd(), "swt3.yaml");
|
|
70
|
+
// Check overwrite protection
|
|
71
|
+
const forceIdx = args.indexOf("--force");
|
|
72
|
+
const force = forceIdx !== -1;
|
|
73
|
+
if (existsSync(outputPath) && !force) {
|
|
74
|
+
console.error("swt3.yaml already exists. Use --force to overwrite.");
|
|
75
|
+
process.exit(1);
|
|
76
|
+
}
|
|
77
|
+
// Parse flags
|
|
78
|
+
const profileIdx = args.indexOf("--profile");
|
|
79
|
+
const tenantIdx = args.indexOf("--tenant");
|
|
80
|
+
const agentIdx = args.indexOf("--agent");
|
|
81
|
+
let profile = profileIdx !== -1 ? args[profileIdx + 1] : "";
|
|
82
|
+
let tenantId = tenantIdx !== -1 ? args[tenantIdx + 1] : "";
|
|
83
|
+
let agentId = agentIdx !== -1 ? args[agentIdx + 1] : "";
|
|
84
|
+
// Validate profile if provided
|
|
85
|
+
if (profile && !PROFILE_NAMES.includes(profile)) {
|
|
86
|
+
console.error(`Unknown profile: '${profile}'`);
|
|
87
|
+
console.error(`Valid profiles: ${PROFILE_NAMES.join(", ")}`);
|
|
88
|
+
process.exit(1);
|
|
89
|
+
}
|
|
90
|
+
// Interactive mode if no profile specified
|
|
91
|
+
if (!profile) {
|
|
92
|
+
const rl = createInterface({ input: process.stdin, output: process.stdout });
|
|
93
|
+
console.log(`\n SWT3 Governance Setup\n`);
|
|
94
|
+
console.log(` Choose a compliance profile:`);
|
|
95
|
+
PROFILE_NAMES.forEach((name, i) => {
|
|
96
|
+
console.log(` ${i + 1}. ${name.padEnd(24)} ${PROFILES[name]}`);
|
|
97
|
+
});
|
|
98
|
+
const choice = await ask(rl, `\n Profile [1-${PROFILE_NAMES.length}]: `);
|
|
99
|
+
const idx = parseInt(choice, 10) - 1;
|
|
100
|
+
if (isNaN(idx) || idx < 0 || idx >= PROFILE_NAMES.length) {
|
|
101
|
+
console.error(" Invalid selection.");
|
|
102
|
+
rl.close();
|
|
103
|
+
process.exit(1);
|
|
104
|
+
}
|
|
105
|
+
profile = PROFILE_NAMES[idx];
|
|
106
|
+
if (!tenantId) {
|
|
107
|
+
tenantId = await ask(rl, " Tenant ID: ");
|
|
108
|
+
}
|
|
109
|
+
if (!agentId) {
|
|
110
|
+
agentId = await ask(rl, " Agent ID [optional]: ");
|
|
111
|
+
}
|
|
112
|
+
rl.close();
|
|
113
|
+
}
|
|
114
|
+
const content = generateInitYaml(profile, tenantId, agentId);
|
|
115
|
+
writeFileSync(outputPath, content, "utf-8");
|
|
116
|
+
console.log(`\n Created: swt3.yaml\n`);
|
|
117
|
+
console.log(` Next: set SWT3_API_KEY in your environment, then:`);
|
|
118
|
+
console.log(` import { Witness } from "@tenova/swt3-ai";`);
|
|
119
|
+
console.log(` const witness = Witness.fromConfig(); // done.\n`);
|
|
120
|
+
}
|
|
121
|
+
async function main() {
|
|
122
|
+
const [, , cmd, ...rest] = process.argv;
|
|
123
|
+
switch (cmd) {
|
|
124
|
+
case "init":
|
|
125
|
+
await handleInit(rest);
|
|
126
|
+
break;
|
|
127
|
+
case "demo": {
|
|
128
|
+
if (rest.includes("--mesh-test")) {
|
|
129
|
+
const { runMeshTest } = await import("./demo.js");
|
|
130
|
+
await runMeshTest();
|
|
131
|
+
}
|
|
132
|
+
else {
|
|
133
|
+
const demo = await import("./demo.js");
|
|
134
|
+
demo.main();
|
|
135
|
+
}
|
|
136
|
+
break;
|
|
137
|
+
}
|
|
138
|
+
case "doctor": {
|
|
139
|
+
if (rest.includes("--friction-test")) {
|
|
140
|
+
const { runFrictionTest, printFrictionResults } = await import("./doctor.js");
|
|
141
|
+
const steps = await runFrictionTest();
|
|
142
|
+
printFrictionResults(steps);
|
|
143
|
+
if (steps.some((s) => s.status === "fail"))
|
|
144
|
+
process.exit(1);
|
|
145
|
+
}
|
|
146
|
+
else {
|
|
147
|
+
const { runDoctorChecks, printDoctorResults } = await import("./doctor.js");
|
|
148
|
+
const checks = runDoctorChecks();
|
|
149
|
+
const jsonFlag = rest.includes("--json");
|
|
150
|
+
printDoctorResults(checks, jsonFlag);
|
|
151
|
+
const hasFail = checks.some((c) => c.status === "fail");
|
|
152
|
+
if (hasFail)
|
|
153
|
+
process.exit(1);
|
|
154
|
+
}
|
|
155
|
+
break;
|
|
156
|
+
}
|
|
157
|
+
case "audit": {
|
|
158
|
+
const { ChainMonitorExporter } = await import("./exporters/chain-monitor.js");
|
|
159
|
+
const fmtIdx = rest.indexOf("--format");
|
|
160
|
+
const format = fmtIdx !== -1 && rest[fmtIdx + 1] ? rest[fmtIdx + 1] : "html";
|
|
161
|
+
const walIdx = rest.indexOf("--wal-path");
|
|
162
|
+
const walDir = walIdx !== -1 && rest[walIdx + 1] ? rest[walIdx + 1] : undefined;
|
|
163
|
+
let tenantId = "UNKNOWN", agentId = "UNKNOWN", clearingLevel = 1;
|
|
164
|
+
try {
|
|
165
|
+
const { loadFullConfig } = await import("./config.js");
|
|
166
|
+
const cfg = loadFullConfig();
|
|
167
|
+
const opts = cfg.witnessOptions;
|
|
168
|
+
tenantId = opts.tenantId ?? tenantId;
|
|
169
|
+
agentId = opts.agentId ?? agentId;
|
|
170
|
+
clearingLevel = opts.clearingLevel ?? clearingLevel;
|
|
171
|
+
}
|
|
172
|
+
catch { /* no config */ }
|
|
173
|
+
const exporter = new ChainMonitorExporter({ walDir, tenantId, agentId, clearingLevel });
|
|
174
|
+
if (format === "json") {
|
|
175
|
+
console.log(exporter.exportJson());
|
|
176
|
+
}
|
|
177
|
+
else {
|
|
178
|
+
const { writeFileSync } = await import("node:fs");
|
|
179
|
+
const html = exporter.exportHtml();
|
|
180
|
+
const outPath = "swt3-audit-report.html";
|
|
181
|
+
writeFileSync(outPath, html, "utf-8");
|
|
182
|
+
console.log(`Audit report saved: ${outPath}`);
|
|
183
|
+
}
|
|
184
|
+
break;
|
|
185
|
+
}
|
|
186
|
+
case "help":
|
|
187
|
+
case "--help":
|
|
188
|
+
case "-h":
|
|
189
|
+
case undefined:
|
|
190
|
+
printHelp();
|
|
191
|
+
break;
|
|
192
|
+
default:
|
|
193
|
+
console.error(`Unknown command: ${cmd}`);
|
|
194
|
+
printHelp();
|
|
195
|
+
process.exit(1);
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
main().catch((err) => {
|
|
199
|
+
console.error(err.message);
|
|
200
|
+
process.exit(1);
|
|
201
|
+
});
|
|
202
|
+
//# sourceMappingURL=cli.js.map
|
package/dist/cli.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
|