@terminals-tech/agent-zero 1.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 (263) hide show
  1. package/README.md +209 -0
  2. package/bin/agent-zero.js +332 -0
  3. package/dist/agency/commandRouter.d.ts +48 -0
  4. package/dist/agency/commandRouter.d.ts.map +1 -0
  5. package/dist/agency/commandRouter.js +343 -0
  6. package/dist/agency/commandRouter.js.map +1 -0
  7. package/dist/agency/runtime.d.ts +66 -0
  8. package/dist/agency/runtime.d.ts.map +1 -0
  9. package/dist/agency/runtime.js +247 -0
  10. package/dist/agency/runtime.js.map +1 -0
  11. package/dist/agency/summaryGenerator.d.ts +39 -0
  12. package/dist/agency/summaryGenerator.d.ts.map +1 -0
  13. package/dist/agency/summaryGenerator.js +110 -0
  14. package/dist/agency/summaryGenerator.js.map +1 -0
  15. package/dist/agency/summaryScheduler.d.ts +33 -0
  16. package/dist/agency/summaryScheduler.d.ts.map +1 -0
  17. package/dist/agency/summaryScheduler.js +68 -0
  18. package/dist/agency/summaryScheduler.js.map +1 -0
  19. package/dist/browser/agent-runtime/RuntimePanel.d.ts +20 -0
  20. package/dist/browser/agent-runtime/RuntimePanel.d.ts.map +1 -0
  21. package/dist/browser/agent-runtime/RuntimePanel.js +203 -0
  22. package/dist/browser/agent-runtime/RuntimePanel.js.map +1 -0
  23. package/dist/browser/agent-runtime/config.d.ts +28 -0
  24. package/dist/browser/agent-runtime/config.d.ts.map +1 -0
  25. package/dist/browser/agent-runtime/config.js +50 -0
  26. package/dist/browser/agent-runtime/config.js.map +1 -0
  27. package/dist/browser/agent-runtime/launcher.d.ts +71 -0
  28. package/dist/browser/agent-runtime/launcher.d.ts.map +1 -0
  29. package/dist/browser/agent-runtime/launcher.js +167 -0
  30. package/dist/browser/agent-runtime/launcher.js.map +1 -0
  31. package/dist/browser/rail-auth-bridge.d.ts +85 -0
  32. package/dist/browser/rail-auth-bridge.d.ts.map +1 -0
  33. package/dist/browser/rail-auth-bridge.js +209 -0
  34. package/dist/browser/rail-auth-bridge.js.map +1 -0
  35. package/dist/channels/index.d.ts +13 -0
  36. package/dist/channels/index.d.ts.map +1 -0
  37. package/dist/channels/index.js +12 -0
  38. package/dist/channels/index.js.map +1 -0
  39. package/dist/channels/moltbook.d.ts +114 -0
  40. package/dist/channels/moltbook.d.ts.map +1 -0
  41. package/dist/channels/moltbook.js +348 -0
  42. package/dist/channels/moltbook.js.map +1 -0
  43. package/dist/channels/sms.d.ts +33 -0
  44. package/dist/channels/sms.d.ts.map +1 -0
  45. package/dist/channels/sms.js +160 -0
  46. package/dist/channels/sms.js.map +1 -0
  47. package/dist/channels/telegram.d.ts +47 -0
  48. package/dist/channels/telegram.d.ts.map +1 -0
  49. package/dist/channels/telegram.js +276 -0
  50. package/dist/channels/telegram.js.map +1 -0
  51. package/dist/channels/twitter.d.ts +93 -0
  52. package/dist/channels/twitter.d.ts.map +1 -0
  53. package/dist/channels/twitter.js +411 -0
  54. package/dist/channels/twitter.js.map +1 -0
  55. package/dist/channels/whatsapp.d.ts +77 -0
  56. package/dist/channels/whatsapp.d.ts.map +1 -0
  57. package/dist/channels/whatsapp.js +514 -0
  58. package/dist/channels/whatsapp.js.map +1 -0
  59. package/dist/checkout/index.d.ts +92 -0
  60. package/dist/checkout/index.d.ts.map +1 -0
  61. package/dist/checkout/index.js +125 -0
  62. package/dist/checkout/index.js.map +1 -0
  63. package/dist/cli/moltbook.d.ts +11 -0
  64. package/dist/cli/moltbook.d.ts.map +1 -0
  65. package/dist/cli/moltbook.js +259 -0
  66. package/dist/cli/moltbook.js.map +1 -0
  67. package/dist/cli/setup.d.ts +10 -0
  68. package/dist/cli/setup.d.ts.map +1 -0
  69. package/dist/cli/setup.js +232 -0
  70. package/dist/cli/setup.js.map +1 -0
  71. package/dist/coherence/absorption.d.ts +141 -0
  72. package/dist/coherence/absorption.d.ts.map +1 -0
  73. package/dist/coherence/absorption.js +343 -0
  74. package/dist/coherence/absorption.js.map +1 -0
  75. package/dist/coherence/crossPlatform.d.ts +55 -0
  76. package/dist/coherence/crossPlatform.d.ts.map +1 -0
  77. package/dist/coherence/crossPlatform.js +219 -0
  78. package/dist/coherence/crossPlatform.js.map +1 -0
  79. package/dist/coherence/identityResolver.d.ts +27 -0
  80. package/dist/coherence/identityResolver.d.ts.map +1 -0
  81. package/dist/coherence/identityResolver.js +102 -0
  82. package/dist/coherence/identityResolver.js.map +1 -0
  83. package/dist/identity/burner.d.ts +100 -0
  84. package/dist/identity/burner.d.ts.map +1 -0
  85. package/dist/identity/burner.js +256 -0
  86. package/dist/identity/burner.js.map +1 -0
  87. package/dist/identity/burnerScheduler.d.ts +18 -0
  88. package/dist/identity/burnerScheduler.d.ts.map +1 -0
  89. package/dist/identity/burnerScheduler.js +82 -0
  90. package/dist/identity/burnerScheduler.js.map +1 -0
  91. package/dist/identity/moltbookBurnerAdapter.d.ts +14 -0
  92. package/dist/identity/moltbookBurnerAdapter.d.ts.map +1 -0
  93. package/dist/identity/moltbookBurnerAdapter.js +82 -0
  94. package/dist/identity/moltbookBurnerAdapter.js.map +1 -0
  95. package/dist/identity/operationalVault.d.ts +108 -0
  96. package/dist/identity/operationalVault.d.ts.map +1 -0
  97. package/dist/identity/operationalVault.js +259 -0
  98. package/dist/identity/operationalVault.js.map +1 -0
  99. package/dist/index.d.ts +43 -0
  100. package/dist/index.d.ts.map +1 -0
  101. package/dist/index.js +57 -0
  102. package/dist/index.js.map +1 -0
  103. package/dist/moltbook/apiErrorHandler.d.ts +48 -0
  104. package/dist/moltbook/apiErrorHandler.d.ts.map +1 -0
  105. package/dist/moltbook/apiErrorHandler.js +125 -0
  106. package/dist/moltbook/apiErrorHandler.js.map +1 -0
  107. package/dist/moltbook/approvalGate.d.ts +81 -0
  108. package/dist/moltbook/approvalGate.d.ts.map +1 -0
  109. package/dist/moltbook/approvalGate.js +211 -0
  110. package/dist/moltbook/approvalGate.js.map +1 -0
  111. package/dist/moltbook/attentionField.d.ts +55 -0
  112. package/dist/moltbook/attentionField.d.ts.map +1 -0
  113. package/dist/moltbook/attentionField.js +163 -0
  114. package/dist/moltbook/attentionField.js.map +1 -0
  115. package/dist/moltbook/contentEnhancer.d.ts +28 -0
  116. package/dist/moltbook/contentEnhancer.d.ts.map +1 -0
  117. package/dist/moltbook/contentEnhancer.js +129 -0
  118. package/dist/moltbook/contentEnhancer.js.map +1 -0
  119. package/dist/moltbook/daemon.d.ts +111 -0
  120. package/dist/moltbook/daemon.d.ts.map +1 -0
  121. package/dist/moltbook/daemon.js +497 -0
  122. package/dist/moltbook/daemon.js.map +1 -0
  123. package/dist/moltbook/observer.d.ts +44 -0
  124. package/dist/moltbook/observer.d.ts.map +1 -0
  125. package/dist/moltbook/observer.js +71 -0
  126. package/dist/moltbook/observer.js.map +1 -0
  127. package/dist/moltbook/responseComposer.d.ts +54 -0
  128. package/dist/moltbook/responseComposer.d.ts.map +1 -0
  129. package/dist/moltbook/responseComposer.js +233 -0
  130. package/dist/moltbook/responseComposer.js.map +1 -0
  131. package/dist/openclaw/gateway.d.ts +45 -0
  132. package/dist/openclaw/gateway.d.ts.map +1 -0
  133. package/dist/openclaw/gateway.js +139 -0
  134. package/dist/openclaw/gateway.js.map +1 -0
  135. package/dist/openclaw/skill.d.ts +185 -0
  136. package/dist/openclaw/skill.d.ts.map +1 -0
  137. package/dist/openclaw/skill.js +297 -0
  138. package/dist/openclaw/skill.js.map +1 -0
  139. package/dist/primitives/index.d.ts +23 -0
  140. package/dist/primitives/index.d.ts.map +1 -0
  141. package/dist/primitives/index.js +27 -0
  142. package/dist/primitives/index.js.map +1 -0
  143. package/dist/primitives/types.d.ts +673 -0
  144. package/dist/primitives/types.d.ts.map +1 -0
  145. package/dist/primitives/types.js +205 -0
  146. package/dist/primitives/types.js.map +1 -0
  147. package/dist/rail/absorptionBridge.d.ts +47 -0
  148. package/dist/rail/absorptionBridge.d.ts.map +1 -0
  149. package/dist/rail/absorptionBridge.js +78 -0
  150. package/dist/rail/absorptionBridge.js.map +1 -0
  151. package/dist/rail/authProtocol.d.ts +32 -0
  152. package/dist/rail/authProtocol.d.ts.map +1 -0
  153. package/dist/rail/authProtocol.js +83 -0
  154. package/dist/rail/authProtocol.js.map +1 -0
  155. package/dist/rail/clientRateLimiter.d.ts +17 -0
  156. package/dist/rail/clientRateLimiter.d.ts.map +1 -0
  157. package/dist/rail/clientRateLimiter.js +64 -0
  158. package/dist/rail/clientRateLimiter.js.map +1 -0
  159. package/dist/rail/index.d.ts +8 -0
  160. package/dist/rail/index.d.ts.map +1 -0
  161. package/dist/rail/index.js +38 -0
  162. package/dist/rail/index.js.map +1 -0
  163. package/dist/rail/jwtVerifier.d.ts +11 -0
  164. package/dist/rail/jwtVerifier.d.ts.map +1 -0
  165. package/dist/rail/jwtVerifier.js +55 -0
  166. package/dist/rail/jwtVerifier.js.map +1 -0
  167. package/dist/rail/logger.d.ts +13 -0
  168. package/dist/rail/logger.d.ts.map +1 -0
  169. package/dist/rail/logger.js +29 -0
  170. package/dist/rail/logger.js.map +1 -0
  171. package/dist/rail/metadataBroadcaster.d.ts +53 -0
  172. package/dist/rail/metadataBroadcaster.d.ts.map +1 -0
  173. package/dist/rail/metadataBroadcaster.js +126 -0
  174. package/dist/rail/metadataBroadcaster.js.map +1 -0
  175. package/dist/rail/persistence.d.ts +57 -0
  176. package/dist/rail/persistence.d.ts.map +1 -0
  177. package/dist/rail/persistence.js +103 -0
  178. package/dist/rail/persistence.js.map +1 -0
  179. package/dist/rail/securityMonitor.d.ts +23 -0
  180. package/dist/rail/securityMonitor.d.ts.map +1 -0
  181. package/dist/rail/securityMonitor.js +52 -0
  182. package/dist/rail/securityMonitor.js.map +1 -0
  183. package/dist/rail/server.d.ts +186 -0
  184. package/dist/rail/server.d.ts.map +1 -0
  185. package/dist/rail/server.js +568 -0
  186. package/dist/rail/server.js.map +1 -0
  187. package/dist/rail/userSessionManager.d.ts +29 -0
  188. package/dist/rail/userSessionManager.d.ts.map +1 -0
  189. package/dist/rail/userSessionManager.js +87 -0
  190. package/dist/rail/userSessionManager.js.map +1 -0
  191. package/dist/rail/wsServer.d.ts +39 -0
  192. package/dist/rail/wsServer.d.ts.map +1 -0
  193. package/dist/rail/wsServer.js +544 -0
  194. package/dist/rail/wsServer.js.map +1 -0
  195. package/dist/resonance/globalKuramoto.d.ts +67 -0
  196. package/dist/resonance/globalKuramoto.d.ts.map +1 -0
  197. package/dist/resonance/globalKuramoto.js +161 -0
  198. package/dist/resonance/globalKuramoto.js.map +1 -0
  199. package/dist/resonance/index.d.ts +12 -0
  200. package/dist/resonance/index.d.ts.map +1 -0
  201. package/dist/resonance/index.js +9 -0
  202. package/dist/resonance/index.js.map +1 -0
  203. package/dist/resonance/kuramoto.d.ts +118 -0
  204. package/dist/resonance/kuramoto.d.ts.map +1 -0
  205. package/dist/resonance/kuramoto.js +212 -0
  206. package/dist/resonance/kuramoto.js.map +1 -0
  207. package/dist/routing/distributedRouter.d.ts +84 -0
  208. package/dist/routing/distributedRouter.d.ts.map +1 -0
  209. package/dist/routing/distributedRouter.js +209 -0
  210. package/dist/routing/distributedRouter.js.map +1 -0
  211. package/dist/routing/index.d.ts +8 -0
  212. package/dist/routing/index.d.ts.map +1 -0
  213. package/dist/routing/index.js +7 -0
  214. package/dist/routing/index.js.map +1 -0
  215. package/dist/routing/thermodynamic.d.ts +91 -0
  216. package/dist/routing/thermodynamic.d.ts.map +1 -0
  217. package/dist/routing/thermodynamic.js +184 -0
  218. package/dist/routing/thermodynamic.js.map +1 -0
  219. package/dist/runtime/agent-zero.d.ts +138 -0
  220. package/dist/runtime/agent-zero.d.ts.map +1 -0
  221. package/dist/runtime/agent-zero.js +435 -0
  222. package/dist/runtime/agent-zero.js.map +1 -0
  223. package/dist/runtime/index.d.ts +13 -0
  224. package/dist/runtime/index.d.ts.map +1 -0
  225. package/dist/runtime/index.js +15 -0
  226. package/dist/runtime/index.js.map +1 -0
  227. package/dist/security/capabilities.d.ts +178 -0
  228. package/dist/security/capabilities.d.ts.map +1 -0
  229. package/dist/security/capabilities.js +270 -0
  230. package/dist/security/capabilities.js.map +1 -0
  231. package/dist/security/channelFirewallMiddleware.d.ts +22 -0
  232. package/dist/security/channelFirewallMiddleware.d.ts.map +1 -0
  233. package/dist/security/channelFirewallMiddleware.js +52 -0
  234. package/dist/security/channelFirewallMiddleware.js.map +1 -0
  235. package/dist/security/index.d.ts +11 -0
  236. package/dist/security/index.d.ts.map +1 -0
  237. package/dist/security/index.js +11 -0
  238. package/dist/security/index.js.map +1 -0
  239. package/dist/security/injectionFirewall.d.ts +47 -0
  240. package/dist/security/injectionFirewall.d.ts.map +1 -0
  241. package/dist/security/injectionFirewall.js +262 -0
  242. package/dist/security/injectionFirewall.js.map +1 -0
  243. package/dist/security/outputSanitizer.d.ts +28 -0
  244. package/dist/security/outputSanitizer.d.ts.map +1 -0
  245. package/dist/security/outputSanitizer.js +66 -0
  246. package/dist/security/outputSanitizer.js.map +1 -0
  247. package/dist/security/sandbox.d.ts +192 -0
  248. package/dist/security/sandbox.d.ts.map +1 -0
  249. package/dist/security/sandbox.js +359 -0
  250. package/dist/security/sandbox.js.map +1 -0
  251. package/dist/security/skillVerify.d.ts +128 -0
  252. package/dist/security/skillVerify.d.ts.map +1 -0
  253. package/dist/security/skillVerify.js +220 -0
  254. package/dist/security/skillVerify.js.map +1 -0
  255. package/dist/security/vault.d.ts +60 -0
  256. package/dist/security/vault.d.ts.map +1 -0
  257. package/dist/security/vault.js +522 -0
  258. package/dist/security/vault.js.map +1 -0
  259. package/dist/utils/persistentRateLimiter.d.ts +69 -0
  260. package/dist/utils/persistentRateLimiter.d.ts.map +1 -0
  261. package/dist/utils/persistentRateLimiter.js +128 -0
  262. package/dist/utils/persistentRateLimiter.js.map +1 -0
  263. package/package.json +95 -0
@@ -0,0 +1,522 @@
1
+ import { randomBytes, pbkdf2, createCipheriv, createDecipheriv, createHash } from 'crypto';
2
+ import { readFile, writeFile, unlink, readdir, mkdir, rmdir, stat, rm } from 'fs/promises';
3
+ import { hostname, userInfo, homedir } from 'os';
4
+ import { join } from 'path';
5
+ import { z } from 'zod';
6
+ // ============================================================================
7
+ // TYPES & SCHEMAS
8
+ // ============================================================================
9
+ const VaultEntrySchema = z.object({
10
+ salt: z.string(),
11
+ iv: z.string(),
12
+ authTag: z.string(),
13
+ ciphertext: z.string(),
14
+ });
15
+ const DeviceSlotSchema = z.object({
16
+ salt: z.string(),
17
+ iv: z.string(),
18
+ authTag: z.string(),
19
+ ciphertext: z.string(),
20
+ addedAt: z.string(),
21
+ label: z.string().optional(),
22
+ });
23
+ const VaultFileV2Schema = z.object({
24
+ version: z.literal(2),
25
+ deviceSlots: z.array(DeviceSlotSchema).min(1),
26
+ entries: z.record(z.string(), VaultEntrySchema),
27
+ });
28
+ const VaultFileV1Schema = z.object({
29
+ masterSalt: z.string().optional(),
30
+ entries: z.record(z.string(), VaultEntrySchema),
31
+ });
32
+ // ============================================================================
33
+ // CONSTANTS
34
+ // ============================================================================
35
+ function getVaultDir() {
36
+ return process.env['VAULT_DIR'] ?? join(homedir(), '.agent-zero');
37
+ }
38
+ function getVaultPath() {
39
+ return join(getVaultDir(), 'vault.enc');
40
+ }
41
+ function getLockPath() {
42
+ return join(getVaultDir(), 'vault.lock');
43
+ }
44
+ const PBKDF2_ITERATIONS = 100_000;
45
+ const KEY_LENGTH = 32; // 256 bits
46
+ const ALGORITHM = 'aes-256-gcm';
47
+ const IV_LENGTH = 12; // GCM recommended IV size
48
+ const SALT_LENGTH = 32;
49
+ // ============================================================================
50
+ // VAULT
51
+ // ============================================================================
52
+ export class Vault {
53
+ masterKey;
54
+ passphrase;
55
+ deviceSlots;
56
+ data = {};
57
+ locked = false;
58
+ version = 2;
59
+ // v1 compat: masterSalt used when persisting in v1 mode (before migration)
60
+ masterSalt;
61
+ constructor(masterKey, passphrase, deviceSlots, masterSalt) {
62
+ this.masterKey = masterKey;
63
+ this.passphrase = passphrase;
64
+ this.deviceSlots = deviceSlots;
65
+ this.masterSalt = masterSalt;
66
+ }
67
+ // ==========================================================================
68
+ // FINGERPRINT
69
+ // ==========================================================================
70
+ /**
71
+ * Native machine fingerprint (ignores VAULT_MACHINE_FINGERPRINT override).
72
+ * Used by addDevice() to register the actual current machine.
73
+ */
74
+ static getNativeFingerprint() {
75
+ const host = hostname();
76
+ const user = userInfo().username;
77
+ const home = homedir();
78
+ return createHash('sha256').update(`${host}:${user}:${home}`).digest('hex');
79
+ }
80
+ /**
81
+ * Auth fingerprint — respects VAULT_MACHINE_FINGERPRINT override.
82
+ * Used for vault open/key derivation.
83
+ */
84
+ static getAuthFingerprint() {
85
+ return process.env['VAULT_MACHINE_FINGERPRINT'] ?? Vault.getNativeFingerprint();
86
+ }
87
+ // ==========================================================================
88
+ // KEY DERIVATION
89
+ // ==========================================================================
90
+ static async deriveDeviceKey(passphrase, fingerprint, salt) {
91
+ const combinedSecret = `${fingerprint}:${passphrase}`;
92
+ return new Promise((resolve, reject) => {
93
+ pbkdf2(combinedSecret, salt, PBKDF2_ITERATIONS, KEY_LENGTH, 'sha512', (err, key) => {
94
+ if (err)
95
+ reject(err);
96
+ else
97
+ resolve(key);
98
+ });
99
+ });
100
+ }
101
+ /** v1 compat: derive key using auth fingerprint (old behavior). */
102
+ static async deriveKeyV1(passphrase, salt) {
103
+ return Vault.deriveDeviceKey(passphrase, Vault.getAuthFingerprint(), salt);
104
+ }
105
+ // ==========================================================================
106
+ // MASTER KEY ENCRYPTION (for device slots)
107
+ // ==========================================================================
108
+ static encryptMasterKey(deviceKey, masterKey) {
109
+ const iv = randomBytes(IV_LENGTH);
110
+ const cipher = createCipheriv(ALGORITHM, deviceKey, iv);
111
+ const ciphertext = Buffer.concat([cipher.update(masterKey), cipher.final()]);
112
+ const authTag = cipher.getAuthTag();
113
+ return {
114
+ iv: iv.toString('hex'),
115
+ authTag: authTag.toString('hex'),
116
+ ciphertext: ciphertext.toString('hex'),
117
+ };
118
+ }
119
+ static decryptMasterKey(deviceKey, slot) {
120
+ const iv = Buffer.from(slot.iv, 'hex');
121
+ const authTag = Buffer.from(slot.authTag, 'hex');
122
+ const ciphertext = Buffer.from(slot.ciphertext, 'hex');
123
+ const decipher = createDecipheriv(ALGORITHM, deviceKey, iv);
124
+ decipher.setAuthTag(authTag);
125
+ return Buffer.concat([decipher.update(ciphertext), decipher.final()]);
126
+ }
127
+ // ==========================================================================
128
+ // FACTORY: create / open
129
+ // ==========================================================================
130
+ static async create(passphrase) {
131
+ await Vault.ensureVaultDirStatic();
132
+ let raw;
133
+ try {
134
+ const content = await readFile(getVaultPath(), 'utf-8');
135
+ raw = JSON.parse(content);
136
+ }
137
+ catch {
138
+ raw = null;
139
+ }
140
+ // No existing vault → create fresh v2
141
+ if (!raw) {
142
+ return Vault.createFreshV2(passphrase);
143
+ }
144
+ // Try v2 format first
145
+ const v2 = VaultFileV2Schema.safeParse(raw);
146
+ if (v2.success) {
147
+ return Vault.openV2(passphrase, v2.data);
148
+ }
149
+ // v1 format (with or without masterSalt wrapper)
150
+ return Vault.openV1(passphrase, raw);
151
+ }
152
+ static async createFreshV2(passphrase) {
153
+ const masterKey = randomBytes(KEY_LENGTH);
154
+ const fingerprint = Vault.getAuthFingerprint();
155
+ const slotSalt = randomBytes(SALT_LENGTH);
156
+ const deviceKey = await Vault.deriveDeviceKey(passphrase, fingerprint, slotSalt);
157
+ const encrypted = Vault.encryptMasterKey(deviceKey, masterKey);
158
+ const slot = {
159
+ salt: slotSalt.toString('hex'),
160
+ ...encrypted,
161
+ addedAt: new Date().toISOString(),
162
+ label: 'initial',
163
+ };
164
+ const vault = new Vault(masterKey, passphrase, [slot]);
165
+ vault.version = 2;
166
+ vault.data = {};
167
+ await vault.persist();
168
+ return vault;
169
+ }
170
+ static async openV2(passphrase, file) {
171
+ const fingerprint = Vault.getAuthFingerprint();
172
+ for (const slot of file.deviceSlots) {
173
+ try {
174
+ const slotSalt = Buffer.from(slot.salt, 'hex');
175
+ const deviceKey = await Vault.deriveDeviceKey(passphrase, fingerprint, slotSalt);
176
+ const masterKey = Vault.decryptMasterKey(deviceKey, slot);
177
+ const vault = new Vault(masterKey, passphrase, [...file.deviceSlots]);
178
+ vault.version = 2;
179
+ vault.data = file.entries;
180
+ return vault;
181
+ }
182
+ catch {
183
+ continue;
184
+ }
185
+ }
186
+ throw new Error('Vault: no device slot matches current fingerprint. '
187
+ + 'Set VAULT_MACHINE_FINGERPRINT=<old-fingerprint> to recover, then run: addDevice()');
188
+ }
189
+ static async openV1(passphrase, raw) {
190
+ // Parse v1 — two sub-formats: { masterSalt, entries } or flat { key: entry }
191
+ let masterSaltHex;
192
+ let entries;
193
+ const v1 = VaultFileV1Schema.safeParse(raw);
194
+ if (v1.success) {
195
+ masterSaltHex = v1.data.masterSalt;
196
+ entries = v1.data.entries;
197
+ }
198
+ else {
199
+ // Legacy flat format
200
+ const flat = z.record(z.string(), VaultEntrySchema).safeParse(raw);
201
+ entries = flat.success ? flat.data : {};
202
+ }
203
+ const salt = masterSaltHex
204
+ ? Buffer.from(masterSaltHex, 'hex')
205
+ : randomBytes(SALT_LENGTH);
206
+ const saltHex = salt.toString('hex');
207
+ const oldKey = await Vault.deriveKeyV1(passphrase, salt);
208
+ // Test if we can decrypt any entry
209
+ let canDecrypt = Object.keys(entries).length === 0; // empty = trivially migratable
210
+ for (const entry of Object.values(entries)) {
211
+ try {
212
+ const iv = Buffer.from(entry.iv, 'hex');
213
+ const authTag = Buffer.from(entry.authTag, 'hex');
214
+ const ct = Buffer.from(entry.ciphertext, 'hex');
215
+ const decipher = createDecipheriv(ALGORITHM, oldKey, iv);
216
+ decipher.setAuthTag(authTag);
217
+ decipher.update(ct);
218
+ decipher.final();
219
+ canDecrypt = true;
220
+ break;
221
+ }
222
+ catch {
223
+ continue;
224
+ }
225
+ }
226
+ if (canDecrypt) {
227
+ // Auto-migrate to v2
228
+ return Vault.migrateV1ToV2(passphrase, oldKey, entries);
229
+ }
230
+ // Can't decrypt — stay v1, warn. Existing "entries return null" behavior preserved.
231
+ console.warn('Vault: fingerprint mismatch. Entries from previous device will return null.');
232
+ console.warn('To migrate: set VAULT_MACHINE_FINGERPRINT=<old-fingerprint>, reopen, then call addDevice().');
233
+ const vault = new Vault(oldKey, passphrase, [], saltHex);
234
+ vault.version = 1;
235
+ vault.data = entries;
236
+ return vault;
237
+ }
238
+ static async migrateV1ToV2(passphrase, oldKey, entries) {
239
+ const newMasterKey = randomBytes(KEY_LENGTH);
240
+ const fingerprint = Vault.getAuthFingerprint();
241
+ // Re-encrypt all entries with new random master key
242
+ const newEntries = {};
243
+ let migrated = 0;
244
+ let dropped = 0;
245
+ for (const [key, entry] of Object.entries(entries)) {
246
+ try {
247
+ // Decrypt with old key
248
+ const iv = Buffer.from(entry.iv, 'hex');
249
+ const authTag = Buffer.from(entry.authTag, 'hex');
250
+ const ct = Buffer.from(entry.ciphertext, 'hex');
251
+ const decipher = createDecipheriv(ALGORITHM, oldKey, iv);
252
+ decipher.setAuthTag(authTag);
253
+ const plaintext = Buffer.concat([decipher.update(ct), decipher.final()]);
254
+ // Re-encrypt with new master key
255
+ const newIv = randomBytes(IV_LENGTH);
256
+ const newSalt = randomBytes(SALT_LENGTH);
257
+ const cipher = createCipheriv(ALGORITHM, newMasterKey, newIv);
258
+ const newCt = Buffer.concat([cipher.update(plaintext), cipher.final()]);
259
+ const newAuthTag = cipher.getAuthTag();
260
+ newEntries[key] = {
261
+ salt: newSalt.toString('hex'),
262
+ iv: newIv.toString('hex'),
263
+ authTag: newAuthTag.toString('hex'),
264
+ ciphertext: newCt.toString('hex'),
265
+ };
266
+ migrated++;
267
+ }
268
+ catch {
269
+ // Entry can't be decrypted (stale from old passphrase) — drop
270
+ dropped++;
271
+ }
272
+ }
273
+ // Create device slot for current auth fingerprint
274
+ const slotSalt = randomBytes(SALT_LENGTH);
275
+ const deviceKey = await Vault.deriveDeviceKey(passphrase, fingerprint, slotSalt);
276
+ const encrypted = Vault.encryptMasterKey(deviceKey, newMasterKey);
277
+ const slot = {
278
+ salt: slotSalt.toString('hex'),
279
+ ...encrypted,
280
+ addedAt: new Date().toISOString(),
281
+ label: 'migrated-from-v1',
282
+ };
283
+ if (migrated > 0 || dropped > 0) {
284
+ console.log(`Vault migrated v1→v2: ${migrated} entries migrated, ${dropped} stale entries dropped`);
285
+ }
286
+ const vault = new Vault(newMasterKey, passphrase, [slot]);
287
+ vault.version = 2;
288
+ vault.data = newEntries;
289
+ await vault.persist();
290
+ return vault;
291
+ }
292
+ // ==========================================================================
293
+ // DEVICE MANAGEMENT
294
+ // ==========================================================================
295
+ /**
296
+ * Register the current machine's native fingerprint as a new device slot.
297
+ * Always uses the NATIVE fingerprint (ignores VAULT_MACHINE_FINGERPRINT override),
298
+ * so you can open with an override and add-device to register the real machine.
299
+ */
300
+ async addDevice(label) {
301
+ if (this.version !== 2) {
302
+ throw new Error('Cannot add device to v1 vault. Open with correct fingerprint first to trigger migration.');
303
+ }
304
+ const fingerprint = Vault.getNativeFingerprint();
305
+ const slotSalt = randomBytes(SALT_LENGTH);
306
+ const deviceKey = await Vault.deriveDeviceKey(this.passphrase, fingerprint, slotSalt);
307
+ const encrypted = Vault.encryptMasterKey(deviceKey, this.masterKey);
308
+ const slot = {
309
+ salt: slotSalt.toString('hex'),
310
+ ...encrypted,
311
+ addedAt: new Date().toISOString(),
312
+ ...(label ? { label } : {}),
313
+ };
314
+ this.deviceSlots.push(slot);
315
+ await this.persist();
316
+ return fingerprint.slice(0, 16); // truncated for display
317
+ }
318
+ /**
319
+ * List registered device slots (no secrets exposed).
320
+ */
321
+ listDevices() {
322
+ return this.deviceSlots.map((slot, i) => ({
323
+ index: i,
324
+ addedAt: slot.addedAt,
325
+ label: slot.label,
326
+ }));
327
+ }
328
+ getVersion() {
329
+ return this.version;
330
+ }
331
+ // ==========================================================================
332
+ // LOCKING
333
+ // ==========================================================================
334
+ static async ensureVaultDirStatic() {
335
+ try {
336
+ await mkdir(getVaultDir(), { recursive: true });
337
+ }
338
+ catch (err) {
339
+ if (err.code !== 'EEXIST')
340
+ throw err;
341
+ }
342
+ }
343
+ async acquireLock() {
344
+ const maxRetries = 50;
345
+ const retryDelay = 100;
346
+ for (let i = 0; i < maxRetries; i++) {
347
+ try {
348
+ await mkdir(getLockPath());
349
+ this.locked = true;
350
+ return;
351
+ }
352
+ catch (err) {
353
+ if (err.code === 'EEXIST') {
354
+ // Check for stale lock (older than 30 seconds)
355
+ const lockStat = await stat(getLockPath()).catch(() => null);
356
+ if (lockStat && Date.now() - lockStat.mtimeMs > 30_000) {
357
+ await rm(getLockPath(), { recursive: true }).catch(() => { });
358
+ try {
359
+ await mkdir(getLockPath());
360
+ this.locked = true;
361
+ return;
362
+ }
363
+ catch {
364
+ // continue retry loop
365
+ }
366
+ }
367
+ await new Promise(resolve => setTimeout(resolve, retryDelay));
368
+ }
369
+ else {
370
+ throw err;
371
+ }
372
+ }
373
+ }
374
+ throw new Error('Failed to acquire vault lock after retries');
375
+ }
376
+ async releaseLock() {
377
+ if (!this.locked)
378
+ return;
379
+ try {
380
+ await rmdir(getLockPath());
381
+ this.locked = false;
382
+ }
383
+ catch (err) {
384
+ if (err.code !== 'ENOENT')
385
+ throw err;
386
+ }
387
+ }
388
+ // ==========================================================================
389
+ // ENCRYPT / DECRYPT (entry-level, using master key)
390
+ // ==========================================================================
391
+ encrypt(plaintext) {
392
+ const salt = randomBytes(SALT_LENGTH);
393
+ const iv = randomBytes(IV_LENGTH);
394
+ const cipher = createCipheriv(ALGORITHM, this.masterKey, iv);
395
+ const ciphertext = Buffer.concat([
396
+ cipher.update(plaintext, 'utf-8'),
397
+ cipher.final(),
398
+ ]);
399
+ const authTag = cipher.getAuthTag();
400
+ return {
401
+ salt: salt.toString('hex'),
402
+ iv: iv.toString('hex'),
403
+ authTag: authTag.toString('hex'),
404
+ ciphertext: ciphertext.toString('hex'),
405
+ };
406
+ }
407
+ decrypt(entry) {
408
+ const iv = Buffer.from(entry.iv, 'hex');
409
+ const authTag = Buffer.from(entry.authTag, 'hex');
410
+ const ciphertext = Buffer.from(entry.ciphertext, 'hex');
411
+ const decipher = createDecipheriv(ALGORITHM, this.masterKey, iv);
412
+ decipher.setAuthTag(authTag);
413
+ const plaintext = Buffer.concat([
414
+ decipher.update(ciphertext),
415
+ decipher.final(),
416
+ ]);
417
+ return plaintext.toString('utf-8');
418
+ }
419
+ // ==========================================================================
420
+ // PUBLIC API
421
+ // ==========================================================================
422
+ async store(key, value) {
423
+ const entry = this.encrypt(value);
424
+ this.data[key] = entry;
425
+ await this.persist();
426
+ }
427
+ async retrieve(key) {
428
+ const entry = this.data[key];
429
+ if (!entry)
430
+ return null;
431
+ try {
432
+ return this.decrypt(entry);
433
+ }
434
+ catch {
435
+ // Silently return null for decrypt failures (expected for mixed-passphrase entries)
436
+ return null;
437
+ }
438
+ }
439
+ async rotate(key, newValue) {
440
+ if (!this.data[key]) {
441
+ throw new Error(`Key "${key}" does not exist`);
442
+ }
443
+ await this.store(key, newValue);
444
+ }
445
+ async delete(key) {
446
+ delete this.data[key];
447
+ await this.persist();
448
+ }
449
+ async list() {
450
+ return Object.keys(this.data);
451
+ }
452
+ async migrateFromPlaintext(dir) {
453
+ let count = 0;
454
+ try {
455
+ const files = await readdir(dir);
456
+ for (const file of files) {
457
+ if (file.startsWith('.'))
458
+ continue;
459
+ const filePath = join(dir, file);
460
+ try {
461
+ const content = await readFile(filePath, 'utf-8');
462
+ await this.store(file, content.trim());
463
+ count++;
464
+ }
465
+ catch (err) {
466
+ console.warn(`Failed to migrate ${file}:`, err);
467
+ }
468
+ }
469
+ }
470
+ catch (err) {
471
+ if (err.code !== 'ENOENT')
472
+ throw err;
473
+ }
474
+ return count;
475
+ }
476
+ async destroy() {
477
+ await this.acquireLock();
478
+ try {
479
+ this.data = {};
480
+ this.deviceSlots = [];
481
+ this.masterKey.fill(0);
482
+ try {
483
+ await unlink(getVaultPath());
484
+ }
485
+ catch (err) {
486
+ if (err.code !== 'ENOENT')
487
+ throw err;
488
+ }
489
+ }
490
+ finally {
491
+ await this.releaseLock();
492
+ }
493
+ }
494
+ // ==========================================================================
495
+ // PERSISTENCE
496
+ // ==========================================================================
497
+ async persist() {
498
+ await this.acquireLock();
499
+ try {
500
+ let file;
501
+ if (this.version === 2) {
502
+ file = { version: 2, deviceSlots: this.deviceSlots, entries: this.data };
503
+ }
504
+ else {
505
+ // v1 fallback (pre-migration)
506
+ file = { masterSalt: this.masterSalt, entries: this.data };
507
+ }
508
+ const serialized = JSON.stringify(file, null, 2);
509
+ await writeFile(getVaultPath(), serialized, { mode: 0o600 });
510
+ }
511
+ finally {
512
+ await this.releaseLock();
513
+ }
514
+ }
515
+ }
516
+ // ============================================================================
517
+ // FACTORY
518
+ // ============================================================================
519
+ export async function createVault(passphrase) {
520
+ return Vault.create(passphrase);
521
+ }
522
+ //# sourceMappingURL=vault.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"vault.js","sourceRoot":"","sources":["../../src/security/vault.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,69 @@
1
+ /**
2
+ * Persistent Rate Limiter
3
+ *
4
+ * Rate limiting with persistent storage via Vault.
5
+ * Survives process restarts and shares state across instances.
6
+ */
7
+ import { Vault } from '../security/vault.js';
8
+ /**
9
+ * Sliding window rate limiter with persistent storage.
10
+ * Stores request timestamps in vault and debounces writes for performance.
11
+ */
12
+ export declare class PersistentSlidingWindowLimiter {
13
+ private timestamps;
14
+ private maxRequests;
15
+ private windowMs;
16
+ private vault;
17
+ private vaultKey;
18
+ private persistTimer;
19
+ private dirty;
20
+ constructor(vault: Vault, key: string, maxRequests: number, windowMs: number);
21
+ /**
22
+ * Load persisted state from vault.
23
+ * Must be called before using the limiter.
24
+ */
25
+ load(): Promise<void>;
26
+ /**
27
+ * Check if a request is allowed and record it.
28
+ * @returns true if request is allowed, false if rate limit exceeded
29
+ */
30
+ allow(): boolean;
31
+ /**
32
+ * Get remaining request quota.
33
+ */
34
+ remaining(): number;
35
+ /**
36
+ * Force persist current state to vault.
37
+ */
38
+ flush(): Promise<void>;
39
+ /**
40
+ * Clean up resources and persist final state.
41
+ */
42
+ destroy(): Promise<void>;
43
+ }
44
+ /**
45
+ * Cooldown-based rate limiter with persistent storage.
46
+ * Enforces minimum time between actions.
47
+ */
48
+ export declare class PersistentCooldownLimiter {
49
+ private lastAction;
50
+ private cooldownMs;
51
+ private vault;
52
+ private vaultKey;
53
+ constructor(vault: Vault, key: string, cooldownMs: number);
54
+ /**
55
+ * Load persisted state from vault.
56
+ * Must be called before using the limiter.
57
+ */
58
+ load(): Promise<void>;
59
+ /**
60
+ * Check if an action is allowed and record it.
61
+ * @returns true if action is allowed, false if still in cooldown
62
+ */
63
+ allow(): Promise<boolean>;
64
+ /**
65
+ * Get remaining cooldown time in milliseconds.
66
+ */
67
+ remainingMs(): number;
68
+ }
69
+ //# sourceMappingURL=persistentRateLimiter.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"persistentRateLimiter.d.ts","sourceRoot":"","sources":["../../src/utils/persistentRateLimiter.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,KAAK,EAAE,MAAM,sBAAsB,CAAC;AAM7C;;;GAGG;AACH,qBAAa,8BAA8B;IACzC,OAAO,CAAC,UAAU,CAAgB;IAClC,OAAO,CAAC,WAAW,CAAS;IAC5B,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,KAAK,CAAQ;IACrB,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,YAAY,CAA+B;IACnD,OAAO,CAAC,KAAK,CAAS;gBAEV,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM;IAO5E;;;OAGG;IACG,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAY3B;;;OAGG;IACH,KAAK,IAAI,OAAO;IAahB;;OAEG;IACH,SAAS,IAAI,MAAM;IAMnB;;OAEG;IACG,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAS5B;;OAEG;IACG,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;CAO/B;AAED;;;GAGG;AACH,qBAAa,yBAAyB;IACpC,OAAO,CAAC,UAAU,CAAK;IACvB,OAAO,CAAC,UAAU,CAAS;IAC3B,OAAO,CAAC,KAAK,CAAQ;IACrB,OAAO,CAAC,QAAQ,CAAS;gBAEb,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM;IAMzD;;;OAGG;IACG,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAQ3B;;;OAGG;IACG,KAAK,IAAI,OAAO,CAAC,OAAO,CAAC;IAW/B;;OAEG;IACH,WAAW,IAAI,MAAM;CAGtB"}