@tracehound/core 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 (166) hide show
  1. package/README.md +125 -0
  2. package/dist/core/agent.d.ts +89 -0
  3. package/dist/core/agent.d.ts.map +1 -0
  4. package/dist/core/agent.js +141 -0
  5. package/dist/core/agent.js.map +1 -0
  6. package/dist/core/audit-chain.d.ts +39 -0
  7. package/dist/core/audit-chain.d.ts.map +1 -0
  8. package/dist/core/audit-chain.js +87 -0
  9. package/dist/core/audit-chain.js.map +1 -0
  10. package/dist/core/cold-storage.d.ts +87 -0
  11. package/dist/core/cold-storage.d.ts.map +1 -0
  12. package/dist/core/cold-storage.js +53 -0
  13. package/dist/core/cold-storage.js.map +1 -0
  14. package/dist/core/evidence-factory.d.ts +85 -0
  15. package/dist/core/evidence-factory.d.ts.map +1 -0
  16. package/dist/core/evidence-factory.js +96 -0
  17. package/dist/core/evidence-factory.js.map +1 -0
  18. package/dist/core/evidence.d.ts +48 -0
  19. package/dist/core/evidence.d.ts.map +1 -0
  20. package/dist/core/evidence.js +135 -0
  21. package/dist/core/evidence.js.map +1 -0
  22. package/dist/core/fail-safe.d.ts +149 -0
  23. package/dist/core/fail-safe.d.ts.map +1 -0
  24. package/dist/core/fail-safe.js +217 -0
  25. package/dist/core/fail-safe.js.map +1 -0
  26. package/dist/core/hound-ipc.d.ts +91 -0
  27. package/dist/core/hound-ipc.d.ts.map +1 -0
  28. package/dist/core/hound-ipc.js +196 -0
  29. package/dist/core/hound-ipc.js.map +1 -0
  30. package/dist/core/hound-pool.d.ts +157 -0
  31. package/dist/core/hound-pool.d.ts.map +1 -0
  32. package/dist/core/hound-pool.js +337 -0
  33. package/dist/core/hound-pool.js.map +1 -0
  34. package/dist/core/hound-process.d.ts +14 -0
  35. package/dist/core/hound-process.d.ts.map +1 -0
  36. package/dist/core/hound-process.js +112 -0
  37. package/dist/core/hound-process.js.map +1 -0
  38. package/dist/core/hound-worker.d.ts +14 -0
  39. package/dist/core/hound-worker.d.ts.map +1 -0
  40. package/dist/core/hound-worker.js +112 -0
  41. package/dist/core/hound-worker.js.map +1 -0
  42. package/dist/core/lane-queue.d.ts +121 -0
  43. package/dist/core/lane-queue.d.ts.map +1 -0
  44. package/dist/core/lane-queue.js +181 -0
  45. package/dist/core/lane-queue.js.map +1 -0
  46. package/dist/core/license-manager.d.ts +128 -0
  47. package/dist/core/license-manager.d.ts.map +1 -0
  48. package/dist/core/license-manager.js +219 -0
  49. package/dist/core/license-manager.js.map +1 -0
  50. package/dist/core/notification-emitter.d.ts +140 -0
  51. package/dist/core/notification-emitter.d.ts.map +1 -0
  52. package/dist/core/notification-emitter.js +197 -0
  53. package/dist/core/notification-emitter.js.map +1 -0
  54. package/dist/core/process-adapter.d.ts +146 -0
  55. package/dist/core/process-adapter.d.ts.map +1 -0
  56. package/dist/core/process-adapter.js +174 -0
  57. package/dist/core/process-adapter.js.map +1 -0
  58. package/dist/core/quarantine.d.ts +95 -0
  59. package/dist/core/quarantine.d.ts.map +1 -0
  60. package/dist/core/quarantine.js +221 -0
  61. package/dist/core/quarantine.js.map +1 -0
  62. package/dist/core/rate-limiter.d.ts +94 -0
  63. package/dist/core/rate-limiter.d.ts.map +1 -0
  64. package/dist/core/rate-limiter.js +156 -0
  65. package/dist/core/rate-limiter.js.map +1 -0
  66. package/dist/core/s3-cold-storage.d.ts +116 -0
  67. package/dist/core/s3-cold-storage.d.ts.map +1 -0
  68. package/dist/core/s3-cold-storage.js +198 -0
  69. package/dist/core/s3-cold-storage.js.map +1 -0
  70. package/dist/core/scheduler.d.ts +126 -0
  71. package/dist/core/scheduler.d.ts.map +1 -0
  72. package/dist/core/scheduler.js +138 -0
  73. package/dist/core/scheduler.js.map +1 -0
  74. package/dist/core/security-state.d.ts +170 -0
  75. package/dist/core/security-state.d.ts.map +1 -0
  76. package/dist/core/security-state.js +156 -0
  77. package/dist/core/security-state.js.map +1 -0
  78. package/dist/core/tier-capacity.d.ts +58 -0
  79. package/dist/core/tier-capacity.d.ts.map +1 -0
  80. package/dist/core/tier-capacity.js +89 -0
  81. package/dist/core/tier-capacity.js.map +1 -0
  82. package/dist/core/tracehound.d.ts +85 -0
  83. package/dist/core/tracehound.d.ts.map +1 -0
  84. package/dist/core/tracehound.js +90 -0
  85. package/dist/core/tracehound.js.map +1 -0
  86. package/dist/core/trust-boundary.d.ts +85 -0
  87. package/dist/core/trust-boundary.d.ts.map +1 -0
  88. package/dist/core/trust-boundary.js +71 -0
  89. package/dist/core/trust-boundary.js.map +1 -0
  90. package/dist/core/watcher.d.ts +153 -0
  91. package/dist/core/watcher.d.ts.map +1 -0
  92. package/dist/core/watcher.js +141 -0
  93. package/dist/core/watcher.js.map +1 -0
  94. package/dist/index.d.ts +53 -0
  95. package/dist/index.d.ts.map +1 -0
  96. package/dist/index.js +112 -0
  97. package/dist/index.js.map +1 -0
  98. package/dist/types/audit.d.ts +45 -0
  99. package/dist/types/audit.d.ts.map +1 -0
  100. package/dist/types/audit.js +5 -0
  101. package/dist/types/audit.js.map +1 -0
  102. package/dist/types/common.d.ts +12 -0
  103. package/dist/types/common.d.ts.map +1 -0
  104. package/dist/types/common.js +5 -0
  105. package/dist/types/common.js.map +1 -0
  106. package/dist/types/config.d.ts +98 -0
  107. package/dist/types/config.d.ts.map +1 -0
  108. package/dist/types/config.js +58 -0
  109. package/dist/types/config.js.map +1 -0
  110. package/dist/types/errors.d.ts +118 -0
  111. package/dist/types/errors.d.ts.map +1 -0
  112. package/dist/types/errors.js +266 -0
  113. package/dist/types/errors.js.map +1 -0
  114. package/dist/types/evidence.d.ts +102 -0
  115. package/dist/types/evidence.d.ts.map +1 -0
  116. package/dist/types/evidence.js +5 -0
  117. package/dist/types/evidence.js.map +1 -0
  118. package/dist/types/index.d.ts +18 -0
  119. package/dist/types/index.d.ts.map +1 -0
  120. package/dist/types/index.js +9 -0
  121. package/dist/types/index.js.map +1 -0
  122. package/dist/types/result.d.ts +62 -0
  123. package/dist/types/result.d.ts.map +1 -0
  124. package/dist/types/result.js +34 -0
  125. package/dist/types/result.js.map +1 -0
  126. package/dist/types/scent.d.ts +55 -0
  127. package/dist/types/scent.d.ts.map +1 -0
  128. package/dist/types/scent.js +5 -0
  129. package/dist/types/scent.js.map +1 -0
  130. package/dist/types/signature.d.ts +47 -0
  131. package/dist/types/signature.d.ts.map +1 -0
  132. package/dist/types/signature.js +68 -0
  133. package/dist/types/signature.js.map +1 -0
  134. package/dist/types/threat.d.ts +38 -0
  135. package/dist/types/threat.d.ts.map +1 -0
  136. package/dist/types/threat.js +18 -0
  137. package/dist/types/threat.js.map +1 -0
  138. package/dist/utils/binary-codec.d.ts +225 -0
  139. package/dist/utils/binary-codec.d.ts.map +1 -0
  140. package/dist/utils/binary-codec.js +266 -0
  141. package/dist/utils/binary-codec.js.map +1 -0
  142. package/dist/utils/compare.d.ts +26 -0
  143. package/dist/utils/compare.d.ts.map +1 -0
  144. package/dist/utils/compare.js +44 -0
  145. package/dist/utils/compare.js.map +1 -0
  146. package/dist/utils/encode.d.ts +39 -0
  147. package/dist/utils/encode.d.ts.map +1 -0
  148. package/dist/utils/encode.js +124 -0
  149. package/dist/utils/encode.js.map +1 -0
  150. package/dist/utils/hash.d.ts +19 -0
  151. package/dist/utils/hash.d.ts.map +1 -0
  152. package/dist/utils/hash.js +25 -0
  153. package/dist/utils/hash.js.map +1 -0
  154. package/dist/utils/id.d.ts +20 -0
  155. package/dist/utils/id.d.ts.map +1 -0
  156. package/dist/utils/id.js +47 -0
  157. package/dist/utils/id.js.map +1 -0
  158. package/dist/utils/runtime.d.ts +24 -0
  159. package/dist/utils/runtime.d.ts.map +1 -0
  160. package/dist/utils/runtime.js +68 -0
  161. package/dist/utils/runtime.js.map +1 -0
  162. package/dist/utils/serialize.d.ts +14 -0
  163. package/dist/utils/serialize.d.ts.map +1 -0
  164. package/dist/utils/serialize.js +27 -0
  165. package/dist/utils/serialize.js.map +1 -0
  166. package/package.json +54 -0
package/README.md ADDED
@@ -0,0 +1,125 @@
1
+ # @tracehound/core
2
+
3
+ Security buffer system for threat quarantine.
4
+ Part of the Tracehound Cyberimmune System.
5
+
6
+ ## Status
7
+
8
+ **Phase 1-4 Complete:** ✅
9
+
10
+ - **Phase 1:** Foundation (Types, Utils)
11
+ - **Phase 2:** Evidence, Quarantine, AuditChain
12
+ - **Phase 3:** Agent, RateLimiter
13
+ - **Phase 4:** HoundPool, Scheduler, Watcher, BinaryCodec
14
+
15
+ ## Installation
16
+
17
+ ```bash
18
+ pnpm add @tracehound/core
19
+ ```
20
+
21
+ ## Core Components
22
+
23
+ ### 1. Agent (`IAgent`)
24
+
25
+ The main entry point. Orchestrates the threat detection flow.
26
+
27
+ - **Stateless:** Depends on injected services.
28
+ - **Fail-safe:** Defaults to "clean" on error.
29
+
30
+ ```ts
31
+ import {
32
+ createAgent,
33
+ createQuarantine,
34
+ createRateLimiter,
35
+ createEvidenceFactory,
36
+ } from '@tracehound/core'
37
+
38
+ const agent = createAgent({ maxPayloadSize: 1_000_000 })
39
+ const result = agent.intercept(scent)
40
+ ```
41
+
42
+ ### 2. Hound Pool (`IHoundPool`)
43
+
44
+ Process-separated child worker pool for evidence processing.
45
+
46
+ - **Containment-Oriented:** Uses process separation and hardening flags; OS sandboxing depends on deployment policy.
47
+ - **Fire-and-Forget:** Agent never awaits detection.
48
+ - **Resilient:** Auto-replenish on crash/timeout.
49
+
50
+ ```ts
51
+ // Activate analysis (returns immediately)
52
+ houndPool.activate(evidence)
53
+ ```
54
+
55
+ ### 3. Watcher (`IWatcher`)
56
+
57
+ Pull-based observability.
58
+
59
+ - **Passive:** Does not emit events (no EventEmitter).
60
+ - **Snapshot:** Provides immutable view of system state.
61
+
62
+ ```ts
63
+ const snapshot = watcher.snapshot()
64
+ console.log(`Threats: ${snapshot.threats.total}`)
65
+ ```
66
+
67
+ ### 4. Scheduler (`IScheduler`)
68
+
69
+ Background task management.
70
+
71
+ - **Jittered:** Prevents timing attacks.
72
+ - **Load-Aware:** Skips ticks if system is busy (`skipIfBusy`).
73
+
74
+ ## Usage Example
75
+
76
+ ```ts
77
+ import {
78
+ createAgent,
79
+ createQuarantine,
80
+ createRateLimiter,
81
+ createEvidenceFactory,
82
+ createHoundPool,
83
+ AuditChain,
84
+ } from '@tracehound/core'
85
+
86
+ // 1. Setup Dependencies
87
+ const auditChain = new AuditChain()
88
+ const quarantine = createQuarantine({ maxCount: 1000 }, auditChain)
89
+ const rateLimiter = createRateLimiter({ windowMs: 60000, maxRequests: 100 })
90
+ const factory = createEvidenceFactory()
91
+
92
+ // 2. Create Agent
93
+ const agent = createAgent({ maxPayloadSize: 1_000_000 }, quarantine, rateLimiter, factory)
94
+
95
+ // 3. Intercept Traffic
96
+ const result = agent.intercept({
97
+ id: 'req-1',
98
+ source: '192.168.1.1',
99
+ payload: { user: 'input' },
100
+ timestamp: Date.now(),
101
+ })
102
+
103
+ if (result.status === 'quarantined') {
104
+ console.log('Threat quarantined:', result.handle.signature)
105
+ }
106
+ ```
107
+
108
+ ## Architecture
109
+
110
+ ```
111
+ [Traffic] → (Agent) → [RateLimiter]
112
+
113
+
114
+ [EvidenceFactory] → (Hash/Compress) → [Evidence]
115
+
116
+
117
+ [Quarantine]
118
+
119
+
120
+ (HoundPool) → [Analysis]
121
+ ```
122
+
123
+ ## License
124
+
125
+ Open-Core — this package is the open-source substrate of the Tracehound ecosystem. See the root [PRICING.md](../../docs/PRICING.md) for details on the commercial satellite packages.
@@ -0,0 +1,89 @@
1
+ /**
2
+ * Agent - core orchestrator for Tracehound intercept flow.
3
+ *
4
+ * SECURITY: Agent does NOT perform threat detection.
5
+ * Agent orchestrates: rate limiting → validation → factory → quarantine.
6
+ *
7
+ * RFC Contract:
8
+ * - If scent.threat present → quarantine
9
+ * - If scent.threat absent → clean
10
+ * - Tracehound DOES NOT make threat decisions
11
+ */
12
+ import type { InterceptResult } from '../types/result.js';
13
+ import type { Scent } from '../types/scent.js';
14
+ import type { IEvidenceFactory } from './evidence-factory.js';
15
+ import type { Quarantine } from './quarantine.js';
16
+ import type { IRateLimiter } from './rate-limiter.js';
17
+ /**
18
+ * Agent configuration (subset of TracehoundConfig).
19
+ */
20
+ export interface AgentConfig {
21
+ /** Maximum payload size in bytes */
22
+ maxPayloadSize: number;
23
+ }
24
+ /**
25
+ * Agent interface.
26
+ */
27
+ export interface IAgent {
28
+ /**
29
+ * Intercept a scent and process according to RFC.
30
+ *
31
+ * Flow:
32
+ * 1. Rate limit check → rate_limited
33
+ * 2. If no threat signal → clean
34
+ * 3. Validate & encode payload → payload_too_large | error
35
+ * 4. Generate signature via factory
36
+ * 5. Check duplicate → ignored
37
+ * 6. Create evidence & quarantine → quarantined
38
+ *
39
+ * @param scent - Input scent to process
40
+ * @returns Intercept result
41
+ */
42
+ intercept(scent: Scent): InterceptResult;
43
+ }
44
+ /**
45
+ * Agent statistics.
46
+ */
47
+ export interface AgentStats {
48
+ /** Total intercepts processed */
49
+ totalIntercepts: number;
50
+ /** Clean (no threat signal) */
51
+ cleanCount: number;
52
+ /** Rate limited */
53
+ rateLimitedCount: number;
54
+ /** Payload validation failures */
55
+ validationFailures: number;
56
+ /** Duplicates ignored */
57
+ ignoredCount: number;
58
+ /** Successfully quarantined */
59
+ quarantinedCount: number;
60
+ /** Errors */
61
+ errorCount: number;
62
+ }
63
+ /**
64
+ * Agent implementation.
65
+ */
66
+ export declare class Agent implements IAgent {
67
+ private readonly config;
68
+ private readonly quarantine;
69
+ private readonly rateLimiter;
70
+ private readonly evidenceFactory;
71
+ private readonly stats;
72
+ constructor(config: AgentConfig, quarantine: Quarantine, rateLimiter: IRateLimiter, evidenceFactory: IEvidenceFactory);
73
+ intercept(scent: Scent): InterceptResult;
74
+ /**
75
+ * Get current agent statistics.
76
+ */
77
+ getStats(): Readonly<AgentStats>;
78
+ }
79
+ /**
80
+ * Create an agent instance.
81
+ *
82
+ * @param config - Agent configuration
83
+ * @param quarantine - Quarantine instance
84
+ * @param rateLimiter - Rate limiter instance
85
+ * @param evidenceFactory - Evidence factory instance
86
+ * @returns Agent instance
87
+ */
88
+ export declare function createAgent(config: AgentConfig, quarantine: Quarantine, rateLimiter: IRateLimiter, evidenceFactory: IEvidenceFactory): IAgent;
89
+ //# sourceMappingURL=agent.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent.d.ts","sourceRoot":"","sources":["../../src/core/agent.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAGH,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAA;AACzD,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAA;AAC9C,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,uBAAuB,CAAA;AAC7D,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,iBAAiB,CAAA;AACjD,OAAO,KAAK,EAAE,YAAY,EAAmB,MAAM,mBAAmB,CAAA;AAEtE;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,oCAAoC;IACpC,cAAc,EAAE,MAAM,CAAA;CACvB;AAED;;GAEG;AACH,MAAM,WAAW,MAAM;IACrB;;;;;;;;;;;;;OAaG;IACH,SAAS,CAAC,KAAK,EAAE,KAAK,GAAG,eAAe,CAAA;CACzC;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,iCAAiC;IACjC,eAAe,EAAE,MAAM,CAAA;IACvB,+BAA+B;IAC/B,UAAU,EAAE,MAAM,CAAA;IAClB,mBAAmB;IACnB,gBAAgB,EAAE,MAAM,CAAA;IACxB,kCAAkC;IAClC,kBAAkB,EAAE,MAAM,CAAA;IAC1B,yBAAyB;IACzB,YAAY,EAAE,MAAM,CAAA;IACpB,+BAA+B;IAC/B,gBAAgB,EAAE,MAAM,CAAA;IACxB,aAAa;IACb,UAAU,EAAE,MAAM,CAAA;CACnB;AAED;;GAEG;AACH,qBAAa,KAAM,YAAW,MAAM;IAYhC,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,UAAU;IAC3B,OAAO,CAAC,QAAQ,CAAC,WAAW;IAC5B,OAAO,CAAC,QAAQ,CAAC,eAAe;IAdlC,OAAO,CAAC,QAAQ,CAAC,KAAK,CAQrB;gBAGkB,MAAM,EAAE,WAAW,EACnB,UAAU,EAAE,UAAU,EACtB,WAAW,EAAE,YAAY,EACzB,eAAe,EAAE,gBAAgB;IAQpD,SAAS,CAAC,KAAK,EAAE,KAAK,GAAG,eAAe;IAmGxC;;OAEG;IACH,QAAQ,IAAI,QAAQ,CAAC,UAAU,CAAC;CAGjC;AAED;;;;;;;;GAQG;AACH,wBAAgB,WAAW,CACzB,MAAM,EAAE,WAAW,EACnB,UAAU,EAAE,UAAU,EACtB,WAAW,EAAE,YAAY,EACzB,eAAe,EAAE,gBAAgB,GAChC,MAAM,CAER"}
@@ -0,0 +1,141 @@
1
+ /**
2
+ * Agent - core orchestrator for Tracehound intercept flow.
3
+ *
4
+ * SECURITY: Agent does NOT perform threat detection.
5
+ * Agent orchestrates: rate limiting → validation → factory → quarantine.
6
+ *
7
+ * RFC Contract:
8
+ * - If scent.threat present → quarantine
9
+ * - If scent.threat absent → clean
10
+ * - Tracehound DOES NOT make threat decisions
11
+ */
12
+ /**
13
+ * Agent implementation.
14
+ */
15
+ export class Agent {
16
+ config;
17
+ quarantine;
18
+ rateLimiter;
19
+ evidenceFactory;
20
+ stats = {
21
+ totalIntercepts: 0,
22
+ cleanCount: 0,
23
+ rateLimitedCount: 0,
24
+ validationFailures: 0,
25
+ ignoredCount: 0,
26
+ quarantinedCount: 0,
27
+ errorCount: 0,
28
+ };
29
+ constructor(config, quarantine, rateLimiter, evidenceFactory) {
30
+ this.config = config;
31
+ this.quarantine = quarantine;
32
+ this.rateLimiter = rateLimiter;
33
+ this.evidenceFactory = evidenceFactory;
34
+ // Validate config
35
+ if (config.maxPayloadSize <= 0) {
36
+ throw new Error('maxPayloadSize must be positive');
37
+ }
38
+ }
39
+ intercept(scent) {
40
+ this.stats.totalIntercepts++;
41
+ try {
42
+ // Step 1: Rate limit check
43
+ const rateResult = this.rateLimiter.check(scent.source);
44
+ if (!rateResult.allowed) {
45
+ this.stats.rateLimitedCount++;
46
+ return {
47
+ status: 'rate_limited',
48
+ retryAfter: rateResult.retryAfter,
49
+ };
50
+ }
51
+ // Step 2: Check for threat signal
52
+ if (!scent.threat) {
53
+ // No threat signal = clean
54
+ // Tracehound does NOT make threat detection decisions
55
+ this.stats.cleanCount++;
56
+ return { status: 'clean' };
57
+ }
58
+ // Step 3: Create evidence via factory
59
+ // Factory handles: validation, encoding, hashing, signature generation
60
+ const creationResult = this.evidenceFactory.create(scent, scent.threat, this.config.maxPayloadSize);
61
+ if (!creationResult.ok) {
62
+ // Check if it's a payload size error
63
+ if (creationResult.error.code === 'AGENT_PAYLOAD_TOO_LARGE') {
64
+ this.stats.validationFailures++;
65
+ return {
66
+ status: 'payload_too_large',
67
+ limit: this.config.maxPayloadSize,
68
+ };
69
+ }
70
+ // Other errors
71
+ this.stats.errorCount++;
72
+ return {
73
+ status: 'error',
74
+ error: creationResult.error,
75
+ };
76
+ }
77
+ const { evidence, signature } = creationResult;
78
+ // Step 4: Check for duplicate in quarantine
79
+ if (this.quarantine.has(signature)) {
80
+ // Duplicate - already have evidence for this signature
81
+ // Evidence was created but not needed, dispose it
82
+ evidence.neutralize('');
83
+ this.stats.ignoredCount++;
84
+ return {
85
+ status: 'ignored',
86
+ signature,
87
+ };
88
+ }
89
+ // Step 5: Insert into quarantine
90
+ const insertResult = this.quarantine.insert(evidence);
91
+ if (insertResult.status === 'duplicate') {
92
+ // Race condition: became duplicate between has() and insert()
93
+ // Evidence already disposed by duplicate detection
94
+ this.stats.ignoredCount++;
95
+ return {
96
+ status: 'ignored',
97
+ signature,
98
+ };
99
+ }
100
+ // Success
101
+ this.stats.quarantinedCount++;
102
+ return {
103
+ status: 'quarantined',
104
+ handle: evidence,
105
+ };
106
+ }
107
+ catch (error) {
108
+ this.stats.errorCount++;
109
+ const tracehoundError = {
110
+ state: 'agent',
111
+ code: 'INTERCEPT_FAILED',
112
+ message: error instanceof Error ? error.message : 'Unknown error during intercept',
113
+ context: { scentId: scent.id },
114
+ recoverable: false,
115
+ };
116
+ return {
117
+ status: 'error',
118
+ error: tracehoundError,
119
+ };
120
+ }
121
+ }
122
+ /**
123
+ * Get current agent statistics.
124
+ */
125
+ getStats() {
126
+ return { ...this.stats };
127
+ }
128
+ }
129
+ /**
130
+ * Create an agent instance.
131
+ *
132
+ * @param config - Agent configuration
133
+ * @param quarantine - Quarantine instance
134
+ * @param rateLimiter - Rate limiter instance
135
+ * @param evidenceFactory - Evidence factory instance
136
+ * @returns Agent instance
137
+ */
138
+ export function createAgent(config, quarantine, rateLimiter, evidenceFactory) {
139
+ return new Agent(config, quarantine, rateLimiter, evidenceFactory);
140
+ }
141
+ //# sourceMappingURL=agent.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent.js","sourceRoot":"","sources":["../../src/core/agent.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,39 @@
1
+ /**
2
+ * AuditChain - cryptographic hash chain for evidence integrity.
3
+ */
4
+ import type { AuditRecord, IAuditChain } from '../types/audit.js';
5
+ import type { EvacuateRecord, NeutralizationRecord } from '../types/evidence.js';
6
+ /** Genesis hash (anchor for chain) */
7
+ export declare const GENESIS_HASH: string;
8
+ /**
9
+ * Cryptographic hash chain for audit integrity.
10
+ * Each record contains hash of previous record.
11
+ * Tampering with any record breaks the chain.
12
+ */
13
+ export declare class AuditChain implements IAuditChain {
14
+ private records;
15
+ private _lastHash;
16
+ get lastHash(): string;
17
+ get length(): number;
18
+ /**
19
+ * Append a record to the chain.
20
+ */
21
+ append(record: NeutralizationRecord | EvacuateRecord): void;
22
+ /**
23
+ * Verify chain integrity.
24
+ */
25
+ verify(): boolean;
26
+ /**
27
+ * Export all records (defensive copy).
28
+ */
29
+ export(): AuditRecord[];
30
+ /**
31
+ * Compute hash for a new record.
32
+ */
33
+ private computeHash;
34
+ /**
35
+ * Recompute hash for verification.
36
+ */
37
+ private recomputeHash;
38
+ }
39
+ //# sourceMappingURL=audit-chain.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-chain.d.ts","sourceRoot":"","sources":["../../src/core/audit-chain.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,KAAK,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AACjE,OAAO,KAAK,EAAE,cAAc,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAA;AAEhF,sCAAsC;AACtC,eAAO,MAAM,YAAY,QAAiB,CAAA;AAE1C;;;;GAIG;AACH,qBAAa,UAAW,YAAW,WAAW;IAC5C,OAAO,CAAC,OAAO,CAAoB;IACnC,OAAO,CAAC,SAAS,CAAuB;IAExC,IAAI,QAAQ,IAAI,MAAM,CAErB;IAED,IAAI,MAAM,IAAI,MAAM,CAEnB;IAED;;OAEG;IACH,MAAM,CAAC,MAAM,EAAE,oBAAoB,GAAG,cAAc,GAAG,IAAI;IAgB3D;;OAEG;IACH,MAAM,IAAI,OAAO;IAqBjB;;OAEG;IACH,MAAM,IAAI,WAAW,EAAE;IAIvB;;OAEG;IACH,OAAO,CAAC,WAAW;IAUnB;;OAEG;IACH,OAAO,CAAC,aAAa;CAStB"}
@@ -0,0 +1,87 @@
1
+ /**
2
+ * AuditChain - cryptographic hash chain for evidence integrity.
3
+ */
4
+ import { createHash } from 'node:crypto';
5
+ /** Genesis hash (anchor for chain) */
6
+ export const GENESIS_HASH = '0'.repeat(64);
7
+ /**
8
+ * Cryptographic hash chain for audit integrity.
9
+ * Each record contains hash of previous record.
10
+ * Tampering with any record breaks the chain.
11
+ */
12
+ export class AuditChain {
13
+ records = [];
14
+ _lastHash = GENESIS_HASH;
15
+ get lastHash() {
16
+ return this._lastHash;
17
+ }
18
+ get length() {
19
+ return this.records.length;
20
+ }
21
+ /**
22
+ * Append a record to the chain.
23
+ */
24
+ append(record) {
25
+ const hash = this.computeHash(record, this._lastHash);
26
+ const auditRecord = {
27
+ id: record.id,
28
+ type: 'status' in record ? 'neutralization' : 'evacuation',
29
+ signature: record.signature,
30
+ timestamp: record.timestamp,
31
+ previousHash: this._lastHash,
32
+ hash,
33
+ };
34
+ this.records.push(auditRecord);
35
+ this._lastHash = hash;
36
+ }
37
+ /**
38
+ * Verify chain integrity.
39
+ */
40
+ verify() {
41
+ let expectedPreviousHash = GENESIS_HASH;
42
+ for (const record of this.records) {
43
+ // Check chain continuity
44
+ if (record.previousHash !== expectedPreviousHash) {
45
+ return false;
46
+ }
47
+ // Check hash integrity
48
+ const computedHash = this.recomputeHash(record);
49
+ if (computedHash !== record.hash) {
50
+ return false;
51
+ }
52
+ expectedPreviousHash = record.hash;
53
+ }
54
+ return true;
55
+ }
56
+ /**
57
+ * Export all records (defensive copy).
58
+ */
59
+ export() {
60
+ return [...this.records];
61
+ }
62
+ /**
63
+ * Compute hash for a new record.
64
+ */
65
+ computeHash(record, previousHash) {
66
+ const data = JSON.stringify({
67
+ id: record.id,
68
+ signature: record.signature,
69
+ timestamp: record.timestamp,
70
+ previousHash,
71
+ });
72
+ return createHash('sha256').update(data).digest('hex');
73
+ }
74
+ /**
75
+ * Recompute hash for verification.
76
+ */
77
+ recomputeHash(record) {
78
+ const data = JSON.stringify({
79
+ id: record.id,
80
+ signature: record.signature,
81
+ timestamp: record.timestamp,
82
+ previousHash: record.previousHash,
83
+ });
84
+ return createHash('sha256').update(data).digest('hex');
85
+ }
86
+ }
87
+ //# sourceMappingURL=audit-chain.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit-chain.js","sourceRoot":"","sources":["../../src/core/audit-chain.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AAIxC,sCAAsC;AACtC,MAAM,CAAC,MAAM,YAAY,GAAG,GAAG,CAAC,MAAM,CAAC,EAAE,CAAC,CAAA;AAE1C;;;;GAIG;AACH,MAAM,OAAO,UAAU;IACb,OAAO,GAAkB,EAAE,CAAA;IAC3B,SAAS,GAAW,YAAY,CAAA;IAExC,IAAI,QAAQ;QACV,OAAO,IAAI,CAAC,SAAS,CAAA;IACvB,CAAC;IAED,IAAI,MAAM;QACR,OAAO,IAAI,CAAC,OAAO,CAAC,MAAM,CAAA;IAC5B,CAAC;IAED;;OAEG;IACH,MAAM,CAAC,MAA6C;QAClD,MAAM,IAAI,GAAG,IAAI,CAAC,WAAW,CAAC,MAAM,EAAE,IAAI,CAAC,SAAS,CAAC,CAAA;QAErD,MAAM,WAAW,GAAgB;YAC/B,EAAE,EAAE,MAAM,CAAC,EAAE;YACb,IAAI,EAAE,QAAQ,IAAI,MAAM,CAAC,CAAC,CAAC,gBAAgB,CAAC,CAAC,CAAC,YAAY;YAC1D,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,YAAY,EAAE,IAAI,CAAC,SAAS;YAC5B,IAAI;SACL,CAAA;QAED,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,CAAA;QAC9B,IAAI,CAAC,SAAS,GAAG,IAAI,CAAA;IACvB,CAAC;IAED;;OAEG;IACH,MAAM;QACJ,IAAI,oBAAoB,GAAG,YAAY,CAAA;QAEvC,KAAK,MAAM,MAAM,IAAI,IAAI,CAAC,OAAO,EAAE,CAAC;YAClC,yBAAyB;YACzB,IAAI,MAAM,CAAC,YAAY,KAAK,oBAAoB,EAAE,CAAC;gBACjD,OAAO,KAAK,CAAA;YACd,CAAC;YAED,uBAAuB;YACvB,MAAM,YAAY,GAAG,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,CAAA;YAC/C,IAAI,YAAY,KAAK,MAAM,CAAC,IAAI,EAAE,CAAC;gBACjC,OAAO,KAAK,CAAA;YACd,CAAC;YAED,oBAAoB,GAAG,MAAM,CAAC,IAAI,CAAA;QACpC,CAAC;QAED,OAAO,IAAI,CAAA;IACb,CAAC;IAED;;OAEG;IACH,MAAM;QACJ,OAAO,CAAC,GAAG,IAAI,CAAC,OAAO,CAAC,CAAA;IAC1B,CAAC;IAED;;OAEG;IACK,WAAW,CAAC,MAA6C,EAAE,YAAoB;QACrF,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC;YAC1B,EAAE,EAAE,MAAM,CAAC,EAAE;YACb,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,YAAY;SACb,CAAC,CAAA;QACF,OAAO,UAAU,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAA;IACxD,CAAC;IAED;;OAEG;IACK,aAAa,CAAC,MAAmB;QACvC,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC;YAC1B,EAAE,EAAE,MAAM,CAAC,EAAE;YACb,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,SAAS,EAAE,MAAM,CAAC,SAAS;YAC3B,YAAY,EAAE,MAAM,CAAC,YAAY;SAClC,CAAC,CAAA;QACF,OAAO,UAAU,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAA;IACxD,CAAC;CACF"}
@@ -0,0 +1,87 @@
1
+ /**
2
+ * Cold Storage Adapter
3
+ *
4
+ * Fire-and-forget interface for archiving evidence to external storage.
5
+ * Used by Quarantine.evacuate() for long-term forensic storage.
6
+ *
7
+ * RFC-0000 INVARIANTS:
8
+ * - write() is fire-and-forget (no blocking hot-path)
9
+ * - Adapter errors are logged, not thrown
10
+ * - Payload must be encoded with encodeWithIntegrity() before write
11
+ */
12
+ import type { EncodedPayload } from '../utils/binary-codec.js';
13
+ /**
14
+ * Cold storage write result.
15
+ */
16
+ export interface ColdStorageWriteResult {
17
+ /** Whether write succeeded */
18
+ success: boolean;
19
+ /** Storage-specific ID (e.g., S3 key, URL) */
20
+ id?: string;
21
+ /** Error message if failed */
22
+ error?: string;
23
+ }
24
+ /**
25
+ * Cold storage read result.
26
+ */
27
+ export interface ColdStorageReadResult {
28
+ /** Whether read succeeded */
29
+ success: boolean;
30
+ /** Encoded payload if found */
31
+ payload?: EncodedPayload;
32
+ /** Error message if failed */
33
+ error?: string;
34
+ }
35
+ /**
36
+ * Cold Storage Adapter interface.
37
+ *
38
+ * Implementations: MemoryColdStorage (testing), S3Adapter, R2Adapter, etc.
39
+ */
40
+ export interface IColdStorageAdapter {
41
+ /**
42
+ * Write encoded evidence to cold storage.
43
+ * Fire-and-forget semantics - caller does not wait.
44
+ *
45
+ * @param id - Unique evidence ID (signature)
46
+ * @param payload - Encoded and hashed payload
47
+ */
48
+ write(id: string, payload: EncodedPayload): Promise<ColdStorageWriteResult>;
49
+ /**
50
+ * Read evidence from cold storage.
51
+ * Used for forensics/evacuation only.
52
+ *
53
+ * @param id - Evidence ID to retrieve
54
+ */
55
+ read(id: string): Promise<ColdStorageReadResult>;
56
+ /**
57
+ * Delete evidence from cold storage.
58
+ * Used for policy-based cleanup.
59
+ *
60
+ * @param id - Evidence ID to delete
61
+ */
62
+ delete(id: string): Promise<boolean>;
63
+ /**
64
+ * Check if storage is available.
65
+ */
66
+ isAvailable(): Promise<boolean>;
67
+ }
68
+ /**
69
+ * In-memory cold storage for testing.
70
+ * NOT for production use.
71
+ */
72
+ export declare class MemoryColdStorage implements IColdStorageAdapter {
73
+ private readonly storage;
74
+ write(id: string, payload: EncodedPayload): Promise<ColdStorageWriteResult>;
75
+ read(id: string): Promise<ColdStorageReadResult>;
76
+ delete(id: string): Promise<boolean>;
77
+ isAvailable(): Promise<boolean>;
78
+ /** Get storage size (testing helper) */
79
+ get size(): number;
80
+ /** Clear all storage (testing helper) */
81
+ clear(): void;
82
+ }
83
+ /**
84
+ * Create an in-memory cold storage adapter for testing.
85
+ */
86
+ export declare function createMemoryColdStorage(): IColdStorageAdapter;
87
+ //# sourceMappingURL=cold-storage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cold-storage.d.ts","sourceRoot":"","sources":["../../src/core/cold-storage.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAA;AAE9D;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACrC,8BAA8B;IAC9B,OAAO,EAAE,OAAO,CAAA;IAChB,8CAA8C;IAC9C,EAAE,CAAC,EAAE,MAAM,CAAA;IACX,8BAA8B;IAC9B,KAAK,CAAC,EAAE,MAAM,CAAA;CACf;AAED;;GAEG;AACH,MAAM,WAAW,qBAAqB;IACpC,6BAA6B;IAC7B,OAAO,EAAE,OAAO,CAAA;IAChB,+BAA+B;IAC/B,OAAO,CAAC,EAAE,cAAc,CAAA;IACxB,8BAA8B;IAC9B,KAAK,CAAC,EAAE,MAAM,CAAA;CACf;AAED;;;;GAIG;AACH,MAAM,WAAW,mBAAmB;IAClC;;;;;;OAMG;IACH,KAAK,CAAC,EAAE,EAAE,MAAM,EAAE,OAAO,EAAE,cAAc,GAAG,OAAO,CAAC,sBAAsB,CAAC,CAAA;IAE3E;;;;;OAKG;IACH,IAAI,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,qBAAqB,CAAC,CAAA;IAEhD;;;;;OAKG;IACH,MAAM,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAA;IAEpC;;OAEG;IACH,WAAW,IAAI,OAAO,CAAC,OAAO,CAAC,CAAA;CAChC;AAMD;;;GAGG;AACH,qBAAa,iBAAkB,YAAW,mBAAmB;IAC3D,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAoC;IAEtD,KAAK,CAAC,EAAE,EAAE,MAAM,EAAE,OAAO,EAAE,cAAc,GAAG,OAAO,CAAC,sBAAsB,CAAC;IAK3E,IAAI,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,qBAAqB,CAAC;IAQhD,MAAM,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAIpC,WAAW,IAAI,OAAO,CAAC,OAAO,CAAC;IAIrC,wCAAwC;IACxC,IAAI,IAAI,IAAI,MAAM,CAEjB;IAED,yCAAyC;IACzC,KAAK,IAAI,IAAI;CAGd;AAED;;GAEG;AACH,wBAAgB,uBAAuB,IAAI,mBAAmB,CAE7D"}
@@ -0,0 +1,53 @@
1
+ /**
2
+ * Cold Storage Adapter
3
+ *
4
+ * Fire-and-forget interface for archiving evidence to external storage.
5
+ * Used by Quarantine.evacuate() for long-term forensic storage.
6
+ *
7
+ * RFC-0000 INVARIANTS:
8
+ * - write() is fire-and-forget (no blocking hot-path)
9
+ * - Adapter errors are logged, not thrown
10
+ * - Payload must be encoded with encodeWithIntegrity() before write
11
+ */
12
+ // ─────────────────────────────────────────────────────────────────────────────
13
+ // In-Memory Implementation (Testing)
14
+ // ─────────────────────────────────────────────────────────────────────────────
15
+ /**
16
+ * In-memory cold storage for testing.
17
+ * NOT for production use.
18
+ */
19
+ export class MemoryColdStorage {
20
+ storage = new Map();
21
+ async write(id, payload) {
22
+ this.storage.set(id, payload);
23
+ return { success: true, id };
24
+ }
25
+ async read(id) {
26
+ const payload = this.storage.get(id);
27
+ if (payload) {
28
+ return { success: true, payload };
29
+ }
30
+ return { success: false, error: 'Not found' };
31
+ }
32
+ async delete(id) {
33
+ return this.storage.delete(id);
34
+ }
35
+ async isAvailable() {
36
+ return true;
37
+ }
38
+ /** Get storage size (testing helper) */
39
+ get size() {
40
+ return this.storage.size;
41
+ }
42
+ /** Clear all storage (testing helper) */
43
+ clear() {
44
+ this.storage.clear();
45
+ }
46
+ }
47
+ /**
48
+ * Create an in-memory cold storage adapter for testing.
49
+ */
50
+ export function createMemoryColdStorage() {
51
+ return new MemoryColdStorage();
52
+ }
53
+ //# sourceMappingURL=cold-storage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cold-storage.js","sourceRoot":"","sources":["../../src/core/cold-storage.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAiEH,gFAAgF;AAChF,qCAAqC;AACrC,gFAAgF;AAEhF;;;GAGG;AACH,MAAM,OAAO,iBAAiB;IACX,OAAO,GAAG,IAAI,GAAG,EAA0B,CAAA;IAE5D,KAAK,CAAC,KAAK,CAAC,EAAU,EAAE,OAAuB;QAC7C,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,EAAE,OAAO,CAAC,CAAA;QAC7B,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,EAAE,EAAE,CAAA;IAC9B,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,EAAU;QACnB,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC,CAAA;QACpC,IAAI,OAAO,EAAE,CAAC;YACZ,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,CAAA;QACnC,CAAC;QACD,OAAO,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,WAAW,EAAE,CAAA;IAC/C,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,EAAU;QACrB,OAAO,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE,CAAC,CAAA;IAChC,CAAC;IAED,KAAK,CAAC,WAAW;QACf,OAAO,IAAI,CAAA;IACb,CAAC;IAED,wCAAwC;IACxC,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,OAAO,CAAC,IAAI,CAAA;IAC1B,CAAC;IAED,yCAAyC;IACzC,KAAK;QACH,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAA;IACtB,CAAC;CACF;AAED;;GAEG;AACH,MAAM,UAAU,uBAAuB;IACrC,OAAO,IAAI,iBAAiB,EAAE,CAAA;AAChC,CAAC"}