mindoodb 0.0.84 → 0.0.86

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 (264) hide show
  1. package/README-server.md +1 -0
  2. package/README.md +6 -4
  3. package/dist/appendonlystores/network/ClientNetworkContentAddressedStore.d.ts +15 -0
  4. package/dist/appendonlystores/network/ClientNetworkContentAddressedStore.d.ts.map +1 -1
  5. package/dist/appendonlystores/network/ClientNetworkContentAddressedStore.js +75 -1
  6. package/dist/appendonlystores/network/ClientNetworkContentAddressedStore.js.map +1 -1
  7. package/dist/appendonlystores/network/HttpTransport.d.ts +9 -1
  8. package/dist/appendonlystores/network/HttpTransport.d.ts.map +1 -1
  9. package/dist/appendonlystores/network/HttpTransport.js +38 -10
  10. package/dist/appendonlystores/network/HttpTransport.js.map +1 -1
  11. package/dist/cloudflare/DurableObjectSql.d.ts +56 -0
  12. package/dist/cloudflare/DurableObjectSql.d.ts.map +1 -0
  13. package/dist/cloudflare/DurableObjectSql.js +180 -0
  14. package/dist/cloudflare/DurableObjectSql.js.map +1 -0
  15. package/dist/cloudflare/MindooDatabaseObject.d.ts +86 -0
  16. package/dist/cloudflare/MindooDatabaseObject.d.ts.map +1 -0
  17. package/dist/cloudflare/MindooDatabaseObject.js +614 -0
  18. package/dist/cloudflare/MindooDatabaseObject.js.map +1 -0
  19. package/dist/cloudflare/MindooServerObject.d.ts +63 -0
  20. package/dist/cloudflare/MindooServerObject.d.ts.map +1 -0
  21. package/dist/cloudflare/MindooServerObject.js +521 -0
  22. package/dist/cloudflare/MindooServerObject.js.map +1 -0
  23. package/dist/cloudflare/WorkersCryptoAdapter.d.ts +7 -0
  24. package/dist/cloudflare/WorkersCryptoAdapter.d.ts.map +1 -0
  25. package/dist/cloudflare/WorkersCryptoAdapter.js +14 -0
  26. package/dist/cloudflare/WorkersCryptoAdapter.js.map +1 -0
  27. package/dist/cloudflare/host.d.ts +49 -0
  28. package/dist/cloudflare/host.d.ts.map +1 -0
  29. package/dist/cloudflare/host.js +104 -0
  30. package/dist/cloudflare/host.js.map +1 -0
  31. package/dist/cloudflare/http.d.ts +91 -0
  32. package/dist/cloudflare/http.d.ts.map +1 -0
  33. package/dist/cloudflare/http.js +266 -0
  34. package/dist/cloudflare/http.js.map +1 -0
  35. package/dist/cloudflare/index.d.ts +12 -0
  36. package/dist/cloudflare/index.d.ts.map +1 -0
  37. package/dist/cloudflare/index.js +20 -0
  38. package/dist/cloudflare/index.js.map +1 -0
  39. package/dist/cloudflare/storeRpc.d.ts +22 -0
  40. package/dist/cloudflare/storeRpc.d.ts.map +1 -0
  41. package/dist/cloudflare/storeRpc.js +85 -0
  42. package/dist/cloudflare/storeRpc.js.map +1 -0
  43. package/dist/cloudflare/types.d.ts +101 -0
  44. package/dist/cloudflare/types.d.ts.map +1 -0
  45. package/dist/cloudflare/types.js +10 -0
  46. package/dist/cloudflare/types.js.map +1 -0
  47. package/dist/cloudflare/worker.d.ts +25 -0
  48. package/dist/cloudflare/worker.d.ts.map +1 -0
  49. package/dist/cloudflare/worker.js +170 -0
  50. package/dist/cloudflare/worker.js.map +1 -0
  51. package/dist/core/BaseMindooDB.d.ts +43 -1
  52. package/dist/core/BaseMindooDB.d.ts.map +1 -1
  53. package/dist/core/BaseMindooDB.js +209 -87
  54. package/dist/core/BaseMindooDB.js.map +1 -1
  55. package/dist/core/BaseMindooTenant.d.ts +14 -0
  56. package/dist/core/BaseMindooTenant.d.ts.map +1 -1
  57. package/dist/core/BaseMindooTenant.js +46 -0
  58. package/dist/core/BaseMindooTenant.js.map +1 -1
  59. package/dist/core/BaseMindooTenantDirectory.d.ts +10 -0
  60. package/dist/core/BaseMindooTenantDirectory.d.ts.map +1 -1
  61. package/dist/core/BaseMindooTenantDirectory.js +79 -8
  62. package/dist/core/BaseMindooTenantDirectory.js.map +1 -1
  63. package/dist/core/ChangeDocDraft.d.ts +133 -0
  64. package/dist/core/ChangeDocDraft.d.ts.map +1 -0
  65. package/dist/core/ChangeDocDraft.js +492 -0
  66. package/dist/core/ChangeDocDraft.js.map +1 -0
  67. package/dist/core/appendonlystores/InMemoryContentAddressedStore.d.ts.map +1 -1
  68. package/dist/core/appendonlystores/InMemoryContentAddressedStore.js +1 -0
  69. package/dist/core/appendonlystores/InMemoryContentAddressedStore.js.map +1 -1
  70. package/dist/core/appendonlystores/network/AuthenticationService.d.ts +8 -0
  71. package/dist/core/appendonlystores/network/AuthenticationService.d.ts.map +1 -1
  72. package/dist/core/appendonlystores/network/AuthenticationService.js +19 -0
  73. package/dist/core/appendonlystores/network/AuthenticationService.js.map +1 -1
  74. package/dist/core/appendonlystores/network/IrohStreamIO.d.ts.map +1 -1
  75. package/dist/core/appendonlystores/network/IrohStreamIO.js +3 -23
  76. package/dist/core/appendonlystores/network/IrohStreamIO.js.map +1 -1
  77. package/dist/core/appendonlystores/network/NetworkTransport.d.ts +7 -1
  78. package/dist/core/appendonlystores/network/NetworkTransport.d.ts.map +1 -1
  79. package/dist/core/appendonlystores/network/types.d.ts +23 -0
  80. package/dist/core/appendonlystores/network/types.d.ts.map +1 -1
  81. package/dist/core/appendonlystores/network/types.js.map +1 -1
  82. package/dist/core/appendonlystores/rpc/storeRpcCodec.d.ts.map +1 -1
  83. package/dist/core/appendonlystores/rpc/storeRpcCodec.js +3 -23
  84. package/dist/core/appendonlystores/rpc/storeRpcCodec.js.map +1 -1
  85. package/dist/core/appendonlystores/sqlite/SqliteContentAddressedStore.d.ts.map +1 -1
  86. package/dist/core/appendonlystores/sqlite/SqliteContentAddressedStore.js +21 -30
  87. package/dist/core/appendonlystores/sqlite/SqliteContentAddressedStore.js.map +1 -1
  88. package/dist/core/appendonlystores/sqlite/SqliteDriver.d.ts +37 -1
  89. package/dist/core/appendonlystores/sqlite/SqliteDriver.d.ts.map +1 -1
  90. package/dist/core/appendonlystores/sqlite/SqliteDriver.js +99 -40
  91. package/dist/core/appendonlystores/sqlite/SqliteDriver.js.map +1 -1
  92. package/dist/core/appendonlystores/syncStores.d.ts.map +1 -1
  93. package/dist/core/appendonlystores/syncStores.js +253 -168
  94. package/dist/core/appendonlystores/syncStores.js.map +1 -1
  95. package/dist/core/appendonlystores/types.d.ts +8 -0
  96. package/dist/core/appendonlystores/types.d.ts.map +1 -1
  97. package/dist/core/appendonlystores/types.js.map +1 -1
  98. package/dist/core/expressions/evaluateExpression.d.ts +8 -0
  99. package/dist/core/expressions/evaluateExpression.d.ts.map +1 -1
  100. package/dist/core/expressions/evaluateExpression.js +29 -4
  101. package/dist/core/expressions/evaluateExpression.js.map +1 -1
  102. package/dist/core/expressions/metadata.js +4 -4
  103. package/dist/core/expressions/metadata.js.map +1 -1
  104. package/dist/core/types.d.ts +61 -2
  105. package/dist/core/types.d.ts.map +1 -1
  106. package/dist/core/types.js.map +1 -1
  107. package/dist/core/uri/MindooURI.d.ts.map +1 -1
  108. package/dist/core/uri/MindooURI.js +3 -24
  109. package/dist/core/uri/MindooURI.js.map +1 -1
  110. package/dist/core/utils/base64.d.ts +17 -0
  111. package/dist/core/utils/base64.d.ts.map +1 -0
  112. package/dist/core/utils/base64.js +54 -0
  113. package/dist/core/utils/base64.js.map +1 -0
  114. package/dist/core/utils/idGeneration.d.ts.map +1 -1
  115. package/dist/core/utils/idGeneration.js +14 -3
  116. package/dist/core/utils/idGeneration.js.map +1 -1
  117. package/dist/node/appendonlystores/BasicOnDiskContentAddressedStore.d.ts.map +1 -1
  118. package/dist/node/appendonlystores/BasicOnDiskContentAddressedStore.js +1 -0
  119. package/dist/node/appendonlystores/BasicOnDiskContentAddressedStore.js.map +1 -1
  120. package/dist/node/server/FsServerDataStore.d.ts +23 -0
  121. package/dist/node/server/FsServerDataStore.d.ts.map +1 -0
  122. package/dist/node/server/FsServerDataStore.js +59 -0
  123. package/dist/node/server/FsServerDataStore.js.map +1 -0
  124. package/dist/node/server/IrohServerEndpoint.d.ts +1 -1
  125. package/dist/node/server/IrohServerEndpoint.d.ts.map +1 -1
  126. package/dist/node/server/IrohServerRpc.d.ts +5 -5
  127. package/dist/node/server/IrohServerRpc.d.ts.map +1 -1
  128. package/dist/node/server/IrohServerRpc.js +1 -1
  129. package/dist/node/server/IrohServerRpc.js.map +1 -1
  130. package/dist/node/server/MindooDBServer.d.ts +29 -150
  131. package/dist/node/server/MindooDBServer.d.ts.map +1 -1
  132. package/dist/node/server/MindooDBServer.js +160 -1568
  133. package/dist/node/server/MindooDBServer.js.map +1 -1
  134. package/dist/node/server/PurgedDocRegistry.d.ts +4 -27
  135. package/dist/node/server/PurgedDocRegistry.d.ts.map +1 -1
  136. package/dist/node/server/PurgedDocRegistry.js +6 -83
  137. package/dist/node/server/PurgedDocRegistry.js.map +1 -1
  138. package/dist/node/server/StoreFactory.d.ts +1 -1
  139. package/dist/node/server/StoreFactory.d.ts.map +1 -1
  140. package/dist/node/server/TenantManager.d.ts +16 -284
  141. package/dist/node/server/TenantManager.d.ts.map +1 -1
  142. package/dist/node/server/TenantManager.js +35 -1168
  143. package/dist/node/server/TenantManager.js.map +1 -1
  144. package/dist/node/server/add-to-network.js +1 -1
  145. package/dist/node/server/add-to-network.js.map +1 -1
  146. package/dist/node/server/compressionMiddleware.d.ts +14 -0
  147. package/dist/node/server/compressionMiddleware.d.ts.map +1 -1
  148. package/dist/node/server/compressionMiddleware.js +46 -3
  149. package/dist/node/server/compressionMiddleware.js.map +1 -1
  150. package/dist/node/server/config.d.ts +11 -15
  151. package/dist/node/server/config.d.ts.map +1 -1
  152. package/dist/node/server/config.js +30 -245
  153. package/dist/node/server/config.js.map +1 -1
  154. package/dist/node/server/expressAdapter.d.ts +23 -0
  155. package/dist/node/server/expressAdapter.d.ts.map +1 -0
  156. package/dist/node/server/expressAdapter.js +108 -0
  157. package/dist/node/server/expressAdapter.js.map +1 -0
  158. package/dist/node/server/nativeIrohStreamIO.d.ts +1 -1
  159. package/dist/node/server/nativeIrohStreamIO.d.ts.map +1 -1
  160. package/dist/node/server/peer/FileClusterAuditStorage.d.ts +16 -0
  161. package/dist/node/server/peer/FileClusterAuditStorage.d.ts.map +1 -0
  162. package/dist/node/server/peer/FileClusterAuditStorage.js +39 -0
  163. package/dist/node/server/peer/FileClusterAuditStorage.js.map +1 -0
  164. package/dist/node/server/peer/IrohPeerLink.d.ts +1 -1
  165. package/dist/node/server/peer/IrohPeerLink.d.ts.map +1 -1
  166. package/dist/node/server/peer/routes.d.ts +10 -44
  167. package/dist/node/server/peer/routes.d.ts.map +1 -1
  168. package/dist/node/server/peer/routes.js +33 -275
  169. package/dist/node/server/peer/routes.js.map +1 -1
  170. package/dist/node/server/resolveServerPassword.js +1 -1
  171. package/dist/node/server/resolveServerPassword.js.map +1 -1
  172. package/dist/node/server/server.js +1 -1
  173. package/dist/node/server/server.js.map +1 -1
  174. package/dist/node/server/serverinit.js +1 -1
  175. package/dist/node/server/serverinit.js.map +1 -1
  176. package/dist/server/CapabilityMatcher.d.ts +60 -0
  177. package/dist/server/CapabilityMatcher.d.ts.map +1 -0
  178. package/dist/server/CapabilityMatcher.js +138 -0
  179. package/dist/server/CapabilityMatcher.js.map +1 -0
  180. package/dist/server/DeviceDiscoveryService.d.ts +36 -0
  181. package/dist/server/DeviceDiscoveryService.d.ts.map +1 -0
  182. package/dist/server/DeviceDiscoveryService.js +165 -0
  183. package/dist/server/DeviceDiscoveryService.js.map +1 -0
  184. package/dist/server/PurgedDocRegistry.d.ts +35 -0
  185. package/dist/server/PurgedDocRegistry.d.ts.map +1 -0
  186. package/dist/server/PurgedDocRegistry.js +90 -0
  187. package/dist/server/PurgedDocRegistry.js.map +1 -0
  188. package/dist/server/ServerDataStore.d.ts +67 -0
  189. package/dist/server/ServerDataStore.d.ts.map +1 -0
  190. package/dist/server/ServerDataStore.js +88 -0
  191. package/dist/server/ServerDataStore.js.map +1 -0
  192. package/dist/server/SyncEventBus.d.ts +39 -0
  193. package/dist/server/SyncEventBus.d.ts.map +1 -0
  194. package/dist/server/SyncEventBus.js +41 -0
  195. package/dist/server/SyncEventBus.js.map +1 -0
  196. package/dist/server/SystemAdminAuth.d.ts +82 -0
  197. package/dist/server/SystemAdminAuth.d.ts.map +1 -0
  198. package/dist/server/SystemAdminAuth.js +228 -0
  199. package/dist/server/SystemAdminAuth.js.map +1 -0
  200. package/dist/server/TenantManager.d.ts +330 -0
  201. package/dist/server/TenantManager.d.ts.map +1 -0
  202. package/dist/server/TenantManager.js +1186 -0
  203. package/dist/server/TenantManager.js.map +1 -0
  204. package/dist/server/http/MindooDBServerCore.d.ts +313 -0
  205. package/dist/server/http/MindooDBServerCore.d.ts.map +1 -0
  206. package/dist/server/http/MindooDBServerCore.js +1403 -0
  207. package/dist/server/http/MindooDBServerCore.js.map +1 -0
  208. package/dist/server/http/types.d.ts +89 -0
  209. package/dist/server/http/types.d.ts.map +1 -0
  210. package/dist/server/http/types.js +29 -0
  211. package/dist/server/http/types.js.map +1 -0
  212. package/dist/server/index.d.ts +32 -0
  213. package/dist/server/index.d.ts.map +1 -0
  214. package/dist/server/index.js +76 -0
  215. package/dist/server/index.js.map +1 -0
  216. package/dist/server/peer/ClusterAuditLog.d.ts +71 -0
  217. package/dist/server/peer/ClusterAuditLog.d.ts.map +1 -0
  218. package/dist/server/peer/ClusterAuditLog.js +81 -0
  219. package/dist/server/peer/ClusterAuditLog.js.map +1 -0
  220. package/dist/server/peer/ClusterJobRunner.d.ts +43 -0
  221. package/dist/server/peer/ClusterJobRunner.d.ts.map +1 -0
  222. package/dist/server/peer/ClusterJobRunner.js +119 -0
  223. package/dist/server/peer/ClusterJobRunner.js.map +1 -0
  224. package/dist/server/peer/ClusterManager.d.ts +149 -0
  225. package/dist/server/peer/ClusterManager.d.ts.map +1 -0
  226. package/dist/server/peer/ClusterManager.js +292 -0
  227. package/dist/server/peer/ClusterManager.js.map +1 -0
  228. package/dist/server/peer/PeerAuthService.d.ts +69 -0
  229. package/dist/server/peer/PeerAuthService.d.ts.map +1 -0
  230. package/dist/server/peer/PeerAuthService.js +208 -0
  231. package/dist/server/peer/PeerAuthService.js.map +1 -0
  232. package/dist/server/peer/PeerReplicator.d.ts +303 -0
  233. package/dist/server/peer/PeerReplicator.d.ts.map +1 -0
  234. package/dist/server/peer/PeerReplicator.js +1071 -0
  235. package/dist/server/peer/PeerReplicator.js.map +1 -0
  236. package/dist/server/peer/clusterHttp.d.ts +113 -0
  237. package/dist/server/peer/clusterHttp.d.ts.map +1 -0
  238. package/dist/server/peer/clusterHttp.js +290 -0
  239. package/dist/server/peer/clusterHttp.js.map +1 -0
  240. package/dist/server/peer/types.d.ts +244 -0
  241. package/dist/server/peer/types.d.ts.map +1 -0
  242. package/dist/server/peer/types.js +189 -0
  243. package/dist/server/peer/types.js.map +1 -0
  244. package/dist/server/rateLimits.d.ts +119 -0
  245. package/dist/server/rateLimits.d.ts.map +1 -0
  246. package/dist/server/rateLimits.js +159 -0
  247. package/dist/server/rateLimits.js.map +1 -0
  248. package/dist/server/serverConfig.d.ts +37 -0
  249. package/dist/server/serverConfig.d.ts.map +1 -0
  250. package/dist/server/serverConfig.js +251 -0
  251. package/dist/server/serverConfig.js.map +1 -0
  252. package/dist/server/timestampProxy.d.ts +129 -0
  253. package/dist/server/timestampProxy.d.ts.map +1 -0
  254. package/dist/server/timestampProxy.js +361 -0
  255. package/dist/server/timestampProxy.js.map +1 -0
  256. package/dist/server/types.d.ts +267 -0
  257. package/dist/server/types.d.ts.map +1 -0
  258. package/dist/server/types.js +56 -0
  259. package/dist/server/types.js.map +1 -0
  260. package/dist/server/validation.d.ts +43 -0
  261. package/dist/server/validation.d.ts.map +1 -0
  262. package/dist/server/validation.js +104 -0
  263. package/dist/server/validation.js.map +1 -0
  264. package/package.json +9 -1
@@ -0,0 +1,88 @@
1
+ "use strict";
2
+ /**
3
+ * Where the server keeps its own small state: the server identity, trusted
4
+ * servers, the server key bag, tenant configs and per-tenant registries.
5
+ *
6
+ * Keys are `/`-separated relative paths, and on Node they are exactly the
7
+ * file paths below the data directory (`server.identity.json`,
8
+ * `trusted-servers.json`, `server.keybag`, `<tenantId>/config.json`,
9
+ * `<tenantId>/purged-docs.json`), so existing servers keep reading their data.
10
+ * Other hosts map the same keys onto their own storage, e.g. a Durable
11
+ * Object's SQLite.
12
+ *
13
+ * The interface is synchronous on purpose: the server code that reads this
14
+ * state (tenant lookup, purge denylist) is synchronous today, and both hosts
15
+ * have synchronous storage (Node `fs`, Durable Object SQLite).
16
+ *
17
+ * Entry payloads never go through here; they live in the content-addressed
18
+ * stores (see {@link ServerStoreProvider}).
19
+ */
20
+ Object.defineProperty(exports, "__esModule", { value: true });
21
+ exports.MemoryServerDataStore = void 0;
22
+ function normalizeKey(key) {
23
+ return key.split("/").filter((part) => part.length > 0).join("/");
24
+ }
25
+ /**
26
+ * Volatile {@link ServerDataStore}: tests, and hosts that seed their state at
27
+ * startup.
28
+ */
29
+ class MemoryServerDataStore {
30
+ constructor() {
31
+ this.values = new Map();
32
+ }
33
+ exists(key) {
34
+ const normalized = normalizeKey(key);
35
+ if (normalized === "")
36
+ return true;
37
+ if (this.values.has(normalized))
38
+ return true;
39
+ const prefix = `${normalized}/`;
40
+ for (const existing of this.values.keys()) {
41
+ if (existing.startsWith(prefix))
42
+ return true;
43
+ }
44
+ return false;
45
+ }
46
+ readText(key) {
47
+ const value = this.values.get(normalizeKey(key));
48
+ if (value === undefined)
49
+ return null;
50
+ return typeof value === "string" ? value : new TextDecoder().decode(value);
51
+ }
52
+ writeText(key, value) {
53
+ this.values.set(normalizeKey(key), value);
54
+ }
55
+ readBytes(key) {
56
+ const value = this.values.get(normalizeKey(key));
57
+ if (value === undefined)
58
+ return null;
59
+ return typeof value === "string" ? new TextEncoder().encode(value) : value.slice();
60
+ }
61
+ writeBytes(key, value) {
62
+ this.values.set(normalizeKey(key), value.slice());
63
+ }
64
+ listDirectories(prefix) {
65
+ const normalized = normalizeKey(prefix);
66
+ const base = normalized === "" ? "" : `${normalized}/`;
67
+ const names = new Set();
68
+ for (const key of this.values.keys()) {
69
+ if (!key.startsWith(base))
70
+ continue;
71
+ const rest = key.substring(base.length);
72
+ const slash = rest.indexOf("/");
73
+ if (slash > 0)
74
+ names.add(rest.substring(0, slash));
75
+ }
76
+ return [...names];
77
+ }
78
+ deleteTree(prefix) {
79
+ const normalized = normalizeKey(prefix);
80
+ for (const key of [...this.values.keys()]) {
81
+ if (normalized === "" || key === normalized || key.startsWith(`${normalized}/`)) {
82
+ this.values.delete(key);
83
+ }
84
+ }
85
+ }
86
+ }
87
+ exports.MemoryServerDataStore = MemoryServerDataStore;
88
+ //# sourceMappingURL=ServerDataStore.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ServerDataStore.js","sourceRoot":"","sources":["../../src/server/ServerDataStore.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,39 @@
1
+ /**
2
+ * In-process pub/sub for sync change events (sync-v5, phase 5).
3
+ *
4
+ * The `putEntries` paths publish a small descriptor after each accepted
5
+ * write; SSE subscribers on `GET /sync/:storeKind/events` forward it to
6
+ * connected clients so they can trigger a pull instead of polling.
7
+ *
8
+ * Deliberately minimal: no history, no replay — a client that reconnects
9
+ * simply runs one normal (cheap, cursor-skipped) sync to catch up.
10
+ */
11
+ /** Payload published for every accepted `putEntries` write. */
12
+ export interface SyncChangeEvent {
13
+ tenantId: string;
14
+ dbId: string;
15
+ /** "docs" | "attachments" */
16
+ storeKind: string;
17
+ /** Store head after the write, when the store supports getStoreHead. */
18
+ epoch?: string;
19
+ maxReceiptOrder?: number;
20
+ /**
21
+ * Name of the trusted peer whose push produced this write, when it came from
22
+ * server-to-server replication rather than a client.
23
+ *
24
+ * The peer replicator uses it to suppress the obvious loop: entries that
25
+ * arrived from peer X must not immediately be pushed back to peer X. They
26
+ * still fan out to every *other* peer, which is how a spoke's write reaches
27
+ * the rest of the mesh through its hub.
28
+ */
29
+ originPeer?: string;
30
+ }
31
+ export type SyncChangeListener = (event: SyncChangeEvent) => void;
32
+ export declare class SyncEventBus {
33
+ private listeners;
34
+ /** Register a listener; returns an unsubscribe function. */
35
+ subscribe(listener: SyncChangeListener): () => void;
36
+ publish(event: SyncChangeEvent): void;
37
+ get listenerCount(): number;
38
+ }
39
+ //# sourceMappingURL=SyncEventBus.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SyncEventBus.d.ts","sourceRoot":"","sources":["../../src/server/SyncEventBus.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,+DAA+D;AAC/D,MAAM,WAAW,eAAe;IAC9B,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,6BAA6B;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,wEAAwE;IACxE,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB;;;;;;;;OAQG;IACH,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,MAAM,kBAAkB,GAAG,CAAC,KAAK,EAAE,eAAe,KAAK,IAAI,CAAC;AAElE,qBAAa,YAAY;IACvB,OAAO,CAAC,SAAS,CAAiC;IAElD,4DAA4D;IAC5D,SAAS,CAAC,QAAQ,EAAE,kBAAkB,GAAG,MAAM,IAAI;IAOnD,OAAO,CAAC,KAAK,EAAE,eAAe,GAAG,IAAI;IAWrC,IAAI,aAAa,IAAI,MAAM,CAE1B;CACF"}
@@ -0,0 +1,41 @@
1
+ "use strict";
2
+ /**
3
+ * In-process pub/sub for sync change events (sync-v5, phase 5).
4
+ *
5
+ * The `putEntries` paths publish a small descriptor after each accepted
6
+ * write; SSE subscribers on `GET /sync/:storeKind/events` forward it to
7
+ * connected clients so they can trigger a pull instead of polling.
8
+ *
9
+ * Deliberately minimal: no history, no replay — a client that reconnects
10
+ * simply runs one normal (cheap, cursor-skipped) sync to catch up.
11
+ */
12
+ Object.defineProperty(exports, "__esModule", { value: true });
13
+ exports.SyncEventBus = void 0;
14
+ class SyncEventBus {
15
+ constructor() {
16
+ this.listeners = new Set();
17
+ }
18
+ /** Register a listener; returns an unsubscribe function. */
19
+ subscribe(listener) {
20
+ this.listeners.add(listener);
21
+ return () => {
22
+ this.listeners.delete(listener);
23
+ };
24
+ }
25
+ publish(event) {
26
+ for (const listener of this.listeners) {
27
+ try {
28
+ listener(event);
29
+ }
30
+ catch {
31
+ // A broken subscriber (e.g. a socket torn down mid-write) must never
32
+ // affect the publisher or other subscribers.
33
+ }
34
+ }
35
+ }
36
+ get listenerCount() {
37
+ return this.listeners.size;
38
+ }
39
+ }
40
+ exports.SyncEventBus = SyncEventBus;
41
+ //# sourceMappingURL=SyncEventBus.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SyncEventBus.js","sourceRoot":"","sources":["../../src/server/SyncEventBus.ts"],"names":[],"mappings":";AAAA;;;;;;;;;GASG;;;AAyBH,MAAa,YAAY;IAAzB;QACU,cAAS,GAAG,IAAI,GAAG,EAAsB,CAAC;IAwBpD,CAAC;IAtBC,4DAA4D;IAC5D,SAAS,CAAC,QAA4B;QACpC,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;QAC7B,OAAO,GAAG,EAAE;YACV,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;QAClC,CAAC,CAAC;IACJ,CAAC;IAED,OAAO,CAAC,KAAsB;QAC5B,KAAK,MAAM,QAAQ,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC;YACtC,IAAI,CAAC;gBACH,QAAQ,CAAC,KAAK,CAAC,CAAC;YAClB,CAAC;YAAC,MAAM,CAAC;gBACP,qEAAqE;gBACrE,6CAA6C;YAC/C,CAAC;QACH,CAAC;IACH,CAAC;IAED,IAAI,aAAa;QACf,OAAO,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;IAC7B,CAAC;CACF;AAzBD,oCAyBC"}
@@ -0,0 +1,82 @@
1
+ /**
2
+ * System admin authentication service.
3
+ *
4
+ * Reuses the existing `AuthenticationService` by providing a
5
+ * `SystemAdminDirectory` adapter that derives user lookup data from
6
+ * the capabilities section of `config.json` rather than a tenant
7
+ * directory. Challenges require both username and publicsignkey so
8
+ * the issued JWT can carry both fields for capability matching.
9
+ */
10
+ import type { CryptoAdapter } from "../core/crypto/CryptoAdapter";
11
+ import type { ServerConfig } from "./types";
12
+ export interface SystemAdminTokenPayload {
13
+ sub: string;
14
+ publicsignkey: string;
15
+ iat: number;
16
+ exp: number;
17
+ }
18
+ export declare class SystemAdminAuthService {
19
+ private challenges;
20
+ /**
21
+ * Hard cap on outstanding challenges (DoS guard). Challenge creation is
22
+ * unauthenticated, so bound the map and evict oldest-first on overflow.
23
+ */
24
+ private static readonly MAX_CHALLENGES;
25
+ private jwtSecret;
26
+ private challengeExpirationMs;
27
+ private tokenExpirationMs;
28
+ private principals;
29
+ private allowTenantCreationWildcardPrincipal;
30
+ private cryptoAdapter;
31
+ /**
32
+ * Optional live lookup: a signing key that is a registered tenant's
33
+ * `adminSigningPublicKey` may obtain a system JWT so it can DELETE that
34
+ * tenant. Capability checks still deny every other `/system/*` route.
35
+ */
36
+ private isTenantAdminSigningKey?;
37
+ constructor(cryptoAdapter: CryptoAdapter, config: ServerConfig, options?: {
38
+ jwtSecret?: Uint8Array;
39
+ challengeExpirationMs?: number;
40
+ tokenExpirationMs?: number;
41
+ isTenantAdminSigningKey?: (publicsignkey: string) => boolean;
42
+ });
43
+ /**
44
+ * Hot-swap the principal list from a new config.
45
+ * In-flight challenges and existing JWTs remain valid (same HMAC secret);
46
+ * removed principals will fail the CapabilityMatcher check on their next request.
47
+ */
48
+ reloadPrincipals(config: ServerConfig): void;
49
+ /**
50
+ * Generate a challenge for a system admin.
51
+ * Both `username` and `publicsignkey` are required so we can bind
52
+ * the issued JWT to a specific keypair.
53
+ */
54
+ generateChallenge(username: string, publicsignkey: string): Promise<string>;
55
+ /**
56
+ * Verify a signed challenge and return a JWT containing both
57
+ * `sub` (username) and `publicsignkey`.
58
+ */
59
+ authenticate(challenge: string, signature: Uint8Array): Promise<{
60
+ success: boolean;
61
+ token?: string;
62
+ error?: string;
63
+ }>;
64
+ /**
65
+ * Validate and decode a system admin JWT.
66
+ */
67
+ validateToken(token: string): Promise<SystemAdminTokenPayload | null>;
68
+ private verifySignature;
69
+ private generateToken;
70
+ private cleanupExpiredChallenges;
71
+ /**
72
+ * Bound the challenge map (DoS guard): if still over the cap after expiry
73
+ * cleanup, drop the oldest entries (Map preserves insertion order).
74
+ */
75
+ private evictChallengesOverCap;
76
+ private base64UrlEncode;
77
+ private base64UrlDecode;
78
+ private uint8ArrayToBase64Url;
79
+ private base64UrlToUint8Array;
80
+ private base64ToUint8Array;
81
+ }
82
+ //# sourceMappingURL=SystemAdminAuth.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SystemAdminAuth.d.ts","sourceRoot":"","sources":["../../src/server/SystemAdminAuth.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAGH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,KAAK,EAAE,YAAY,EAAwB,MAAM,SAAS,CAAC;AAUlE,MAAM,WAAW,uBAAuB;IACtC,GAAG,EAAE,MAAM,CAAC;IACZ,aAAa,EAAE,MAAM,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;CACb;AAeD,qBAAa,sBAAsB;IACjC,OAAO,CAAC,UAAU,CAA2C;IAC7D;;;OAGG;IACH,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,cAAc,CAAU;IAChD,OAAO,CAAC,SAAS,CAAa;IAC9B,OAAO,CAAC,qBAAqB,CAAS;IACtC,OAAO,CAAC,iBAAiB,CAAS;IAClC,OAAO,CAAC,UAAU,CAAyB;IAC3C,OAAO,CAAC,oCAAoC,CAAU;IACtD,OAAO,CAAC,aAAa,CAAgB;IACrC;;;;OAIG;IACH,OAAO,CAAC,uBAAuB,CAAC,CAAqC;gBAGnE,aAAa,EAAE,aAAa,EAC5B,MAAM,EAAE,YAAY,EACpB,OAAO,CAAC,EAAE;QACR,SAAS,CAAC,EAAE,UAAU,CAAC;QACvB,qBAAqB,CAAC,EAAE,MAAM,CAAC;QAC/B,iBAAiB,CAAC,EAAE,MAAM,CAAC;QAC3B,uBAAuB,CAAC,EAAE,CAAC,aAAa,EAAE,MAAM,KAAK,OAAO,CAAC;KAC9D;IAaH;;;;OAIG;IACH,gBAAgB,CAAC,MAAM,EAAE,YAAY,GAAG,IAAI;IAM5C;;;;OAIG;IACG,iBAAiB,CACrB,QAAQ,EAAE,MAAM,EAChB,aAAa,EAAE,MAAM,GACpB,OAAO,CAAC,MAAM,CAAC;IAiClB;;;OAGG;IACG,YAAY,CAChB,SAAS,EAAE,MAAM,EACjB,SAAS,EAAE,UAAU,GACpB,OAAO,CAAC;QAAE,OAAO,EAAE,OAAO,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IA+BhE;;OAEG;IACG,aAAa,CACjB,KAAK,EAAE,MAAM,GACZ,OAAO,CAAC,uBAAuB,GAAG,IAAI,CAAC;YAuD5B,eAAe;YAsCf,aAAa;IAuC3B,OAAO,CAAC,wBAAwB;IAShC;;;OAGG;IACH,OAAO,CAAC,sBAAsB;IAW9B,OAAO,CAAC,eAAe;IAKvB,OAAO,CAAC,eAAe;IAMvB,OAAO,CAAC,qBAAqB;IAS7B,OAAO,CAAC,qBAAqB;IAW7B,OAAO,CAAC,kBAAkB;CAQ3B"}
@@ -0,0 +1,228 @@
1
+ "use strict";
2
+ /**
3
+ * System admin authentication service.
4
+ *
5
+ * Reuses the existing `AuthenticationService` by providing a
6
+ * `SystemAdminDirectory` adapter that derives user lookup data from
7
+ * the capabilities section of `config.json` rather than a tenant
8
+ * directory. Challenges require both username and publicsignkey so
9
+ * the issued JWT can carry both fields for capability matching.
10
+ */
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.SystemAdminAuthService = void 0;
13
+ const idGeneration_1 = require("../core/utils/idGeneration");
14
+ const serverConfig_1 = require("./serverConfig");
15
+ // ---------------------------------------------------------------------------
16
+ // SystemAdminAuthService
17
+ // ---------------------------------------------------------------------------
18
+ class SystemAdminAuthService {
19
+ constructor(cryptoAdapter, config, options) {
20
+ this.challenges = new Map();
21
+ this.cryptoAdapter = cryptoAdapter;
22
+ this.principals = (0, serverConfig_1.extractAllPrincipals)(config);
23
+ this.allowTenantCreationWildcardPrincipal =
24
+ (0, serverConfig_1.hasTenantCreationWildcardPrincipal)(config);
25
+ this.isTenantAdminSigningKey = options?.isTenantAdminSigningKey;
26
+ this.jwtSecret =
27
+ options?.jwtSecret ?? cryptoAdapter.getRandomValues(new Uint8Array(32));
28
+ this.challengeExpirationMs = options?.challengeExpirationMs ?? 5 * 60 * 1000;
29
+ this.tokenExpirationMs = options?.tokenExpirationMs ?? 60 * 60 * 1000;
30
+ }
31
+ /**
32
+ * Hot-swap the principal list from a new config.
33
+ * In-flight challenges and existing JWTs remain valid (same HMAC secret);
34
+ * removed principals will fail the CapabilityMatcher check on their next request.
35
+ */
36
+ reloadPrincipals(config) {
37
+ this.principals = (0, serverConfig_1.extractAllPrincipals)(config);
38
+ this.allowTenantCreationWildcardPrincipal =
39
+ (0, serverConfig_1.hasTenantCreationWildcardPrincipal)(config);
40
+ }
41
+ /**
42
+ * Generate a challenge for a system admin.
43
+ * Both `username` and `publicsignkey` are required so we can bind
44
+ * the issued JWT to a specific keypair.
45
+ */
46
+ async generateChallenge(username, publicsignkey) {
47
+ const normalizedUsername = username.toLowerCase();
48
+ const found = this.principals.some((p) => p.username.toLowerCase() === normalizedUsername &&
49
+ p.publicsignkey === publicsignkey);
50
+ if (!found &&
51
+ !this.allowTenantCreationWildcardPrincipal &&
52
+ !this.isTenantAdminSigningKey?.(publicsignkey)) {
53
+ throw new Error("Unknown system admin principal");
54
+ }
55
+ const challenge = (0, idGeneration_1.generateRandomUuid)();
56
+ const now = Date.now();
57
+ this.challenges.set(challenge, {
58
+ challenge,
59
+ username,
60
+ publicsignkey,
61
+ createdAt: now,
62
+ expiresAt: now + this.challengeExpirationMs,
63
+ used: false,
64
+ });
65
+ this.cleanupExpiredChallenges();
66
+ this.evictChallengesOverCap();
67
+ return challenge;
68
+ }
69
+ /**
70
+ * Verify a signed challenge and return a JWT containing both
71
+ * `sub` (username) and `publicsignkey`.
72
+ */
73
+ async authenticate(challenge, signature) {
74
+ const stored = this.challenges.get(challenge);
75
+ if (!stored) {
76
+ return { success: false, error: "Challenge not found or expired" };
77
+ }
78
+ if (Date.now() > stored.expiresAt) {
79
+ this.challenges.delete(challenge);
80
+ return { success: false, error: "Challenge expired" };
81
+ }
82
+ if (stored.used) {
83
+ return { success: false, error: "Challenge already used" };
84
+ }
85
+ stored.used = true;
86
+ const isValid = await this.verifySignature(challenge, signature, stored.publicsignkey);
87
+ if (!isValid) {
88
+ return { success: false, error: "Invalid signature" };
89
+ }
90
+ const token = await this.generateToken(stored.username, stored.publicsignkey);
91
+ return { success: true, token };
92
+ }
93
+ /**
94
+ * Validate and decode a system admin JWT.
95
+ */
96
+ async validateToken(token) {
97
+ const parts = token.split(".");
98
+ if (parts.length !== 3)
99
+ return null;
100
+ const [headerB64, payloadB64, signatureB64] = parts;
101
+ try {
102
+ // Pin the JWT algorithm to HS256 (audit, Low: alg pinning): reject any
103
+ // other declared `alg` to block algorithm-confusion attacks.
104
+ const header = JSON.parse(this.base64UrlDecode(headerB64));
105
+ if (header.alg !== "HS256")
106
+ return null;
107
+ const subtle = this.cryptoAdapter.getSubtle();
108
+ const signingKey = await subtle.importKey("raw", this.jwtSecret.buffer, { name: "HMAC", hash: "SHA-256" }, false, ["verify"]);
109
+ const dataToVerify = new TextEncoder().encode(`${headerB64}.${payloadB64}`);
110
+ const sig = this.base64UrlToUint8Array(signatureB64);
111
+ const isValid = await subtle.verify("HMAC", signingKey, sig.buffer.slice(sig.byteOffset, sig.byteOffset + sig.byteLength), dataToVerify.buffer);
112
+ if (!isValid)
113
+ return null;
114
+ const payload = JSON.parse(this.base64UrlDecode(payloadB64));
115
+ const now = Math.floor(Date.now() / 1000);
116
+ if (payload.exp < now)
117
+ return null;
118
+ return payload;
119
+ }
120
+ catch {
121
+ return null;
122
+ }
123
+ }
124
+ // -----------------------------------------------------------------------
125
+ // Private helpers
126
+ // -----------------------------------------------------------------------
127
+ async verifySignature(message, signature, publicKeyPem) {
128
+ const subtle = this.cryptoAdapter.getSubtle();
129
+ try {
130
+ const pemContents = publicKeyPem
131
+ .replace(/-----BEGIN PUBLIC KEY-----/g, "")
132
+ .replace(/-----END PUBLIC KEY-----/g, "")
133
+ .replace(/\s/g, "");
134
+ const keyData = this.base64ToUint8Array(pemContents);
135
+ const publicKey = await subtle.importKey("spki", keyData.buffer, { name: "Ed25519" }, false, ["verify"]);
136
+ const messageBytes = new TextEncoder().encode(message);
137
+ return await subtle.verify({ name: "Ed25519" }, publicKey, signature.buffer.slice(signature.byteOffset, signature.byteOffset + signature.byteLength), messageBytes.buffer);
138
+ }
139
+ catch {
140
+ return false;
141
+ }
142
+ }
143
+ async generateToken(username, publicsignkey) {
144
+ const subtle = this.cryptoAdapter.getSubtle();
145
+ const now = Math.floor(Date.now() / 1000);
146
+ const payload = {
147
+ sub: username,
148
+ publicsignkey,
149
+ iat: now,
150
+ exp: now + Math.floor(this.tokenExpirationMs / 1000),
151
+ };
152
+ const header = { alg: "HS256", typ: "JWT" };
153
+ const headerB64 = this.base64UrlEncode(JSON.stringify(header));
154
+ const payloadB64 = this.base64UrlEncode(JSON.stringify(payload));
155
+ const signingKey = await subtle.importKey("raw", this.jwtSecret.buffer, { name: "HMAC", hash: "SHA-256" }, false, ["sign"]);
156
+ const dataToSign = new TextEncoder().encode(`${headerB64}.${payloadB64}`);
157
+ const signature = await subtle.sign("HMAC", signingKey, dataToSign.buffer);
158
+ const signatureB64 = this.uint8ArrayToBase64Url(new Uint8Array(signature));
159
+ return `${headerB64}.${payloadB64}.${signatureB64}`;
160
+ }
161
+ cleanupExpiredChallenges() {
162
+ const now = Date.now();
163
+ for (const [key, ch] of this.challenges) {
164
+ if (ch.expiresAt < now) {
165
+ this.challenges.delete(key);
166
+ }
167
+ }
168
+ }
169
+ /**
170
+ * Bound the challenge map (DoS guard): if still over the cap after expiry
171
+ * cleanup, drop the oldest entries (Map preserves insertion order).
172
+ */
173
+ evictChallengesOverCap() {
174
+ let overflow = this.challenges.size - SystemAdminAuthService.MAX_CHALLENGES;
175
+ if (overflow <= 0)
176
+ return;
177
+ for (const key of this.challenges.keys()) {
178
+ if (overflow-- <= 0)
179
+ break;
180
+ this.challenges.delete(key);
181
+ }
182
+ }
183
+ // Base64 utilities
184
+ base64UrlEncode(str) {
185
+ const base64 = btoa(str);
186
+ return base64.replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
187
+ }
188
+ base64UrlDecode(str) {
189
+ let base64 = str.replace(/-/g, "+").replace(/_/g, "/");
190
+ while (base64.length % 4)
191
+ base64 += "=";
192
+ return atob(base64);
193
+ }
194
+ uint8ArrayToBase64Url(bytes) {
195
+ let binary = "";
196
+ for (let i = 0; i < bytes.length; i++) {
197
+ binary += String.fromCharCode(bytes[i]);
198
+ }
199
+ const base64 = btoa(binary);
200
+ return base64.replace(/\+/g, "-").replace(/\//g, "_").replace(/=/g, "");
201
+ }
202
+ base64UrlToUint8Array(str) {
203
+ let base64 = str.replace(/-/g, "+").replace(/_/g, "/");
204
+ while (base64.length % 4)
205
+ base64 += "=";
206
+ const binary = atob(base64);
207
+ const bytes = new Uint8Array(binary.length);
208
+ for (let i = 0; i < binary.length; i++) {
209
+ bytes[i] = binary.charCodeAt(i);
210
+ }
211
+ return bytes;
212
+ }
213
+ base64ToUint8Array(base64) {
214
+ const binary = atob(base64);
215
+ const bytes = new Uint8Array(binary.length);
216
+ for (let i = 0; i < binary.length; i++) {
217
+ bytes[i] = binary.charCodeAt(i);
218
+ }
219
+ return bytes;
220
+ }
221
+ }
222
+ exports.SystemAdminAuthService = SystemAdminAuthService;
223
+ /**
224
+ * Hard cap on outstanding challenges (DoS guard). Challenge creation is
225
+ * unauthenticated, so bound the map and evict oldest-first on overflow.
226
+ */
227
+ SystemAdminAuthService.MAX_CHALLENGES = 10000;
228
+ //# sourceMappingURL=SystemAdminAuth.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SystemAdminAuth.js","sourceRoot":"","sources":["../../src/server/SystemAdminAuth.ts"],"names":[],"mappings":"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"}