stellavault 0.2.0 → 0.2.1

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 (390) hide show
  1. package/package.json +1 -1
  2. package/packages/core/dist/api/dashboard.d.ts +3 -0
  3. package/packages/core/{src/api/dashboard.ts → dist/api/dashboard.js} +8 -11
  4. package/packages/core/dist/api/graph-data.d.ts +11 -0
  5. package/packages/core/dist/api/graph-data.js +255 -0
  6. package/packages/core/dist/api/pwa.d.ts +3 -0
  7. package/packages/core/{src/api/pwa.ts → dist/api/pwa.js} +27 -32
  8. package/packages/core/dist/api/server.d.ts +16 -0
  9. package/packages/core/dist/api/server.js +647 -0
  10. package/packages/core/dist/capture/voice.d.ts +24 -0
  11. package/packages/core/dist/capture/voice.js +135 -0
  12. package/packages/core/{src/cloud/index.ts → dist/cloud/index.d.ts} +1 -0
  13. package/packages/core/dist/cloud/index.js +2 -0
  14. package/packages/core/dist/cloud/sync.d.ts +29 -0
  15. package/packages/core/dist/cloud/sync.js +137 -0
  16. package/packages/core/dist/config.d.ts +27 -0
  17. package/packages/core/dist/config.js +55 -0
  18. package/packages/core/dist/federation/credits.d.ts +26 -0
  19. package/packages/core/dist/federation/credits.js +56 -0
  20. package/packages/core/dist/federation/identity.d.ts +14 -0
  21. package/packages/core/dist/federation/identity.js +74 -0
  22. package/packages/core/{src/federation/index.ts → dist/federation/index.d.ts} +1 -2
  23. package/packages/core/dist/federation/index.js +5 -0
  24. package/packages/core/dist/federation/node.d.ts +31 -0
  25. package/packages/core/dist/federation/node.js +216 -0
  26. package/packages/core/dist/federation/privacy.d.ts +8 -0
  27. package/packages/core/dist/federation/privacy.js +40 -0
  28. package/packages/core/dist/federation/reputation.d.ts +37 -0
  29. package/packages/core/dist/federation/reputation.js +139 -0
  30. package/packages/core/dist/federation/search.d.ts +19 -0
  31. package/packages/core/dist/federation/search.js +101 -0
  32. package/packages/core/dist/federation/sharing.d.ts +72 -0
  33. package/packages/core/dist/federation/sharing.js +246 -0
  34. package/packages/core/dist/federation/trust.d.ts +15 -0
  35. package/packages/core/dist/federation/trust.js +60 -0
  36. package/packages/core/dist/federation/types.d.ts +40 -0
  37. package/packages/core/dist/federation/types.js +3 -0
  38. package/packages/core/dist/i18n/index.d.ts +6 -0
  39. package/packages/core/dist/i18n/index.js +81 -0
  40. package/packages/core/{src/index.ts → dist/index.d.ts} +46 -65
  41. package/packages/core/dist/index.js +69 -0
  42. package/packages/core/dist/indexer/chunker.d.ts +14 -0
  43. package/packages/core/dist/indexer/chunker.js +148 -0
  44. package/packages/core/dist/indexer/embedder.d.ts +8 -0
  45. package/packages/core/dist/indexer/embedder.js +3 -0
  46. package/packages/core/dist/indexer/index.d.ts +28 -0
  47. package/packages/core/dist/indexer/index.js +74 -0
  48. package/packages/core/dist/indexer/local-embedder.d.ts +3 -0
  49. package/packages/core/dist/indexer/local-embedder.js +29 -0
  50. package/packages/core/dist/indexer/scanner.d.ts +11 -0
  51. package/packages/core/dist/indexer/scanner.js +137 -0
  52. package/packages/core/dist/indexer/watcher.d.ts +19 -0
  53. package/packages/core/dist/indexer/watcher.js +49 -0
  54. package/packages/core/dist/intelligence/contradiction-detector.d.ts +20 -0
  55. package/packages/core/dist/intelligence/contradiction-detector.js +115 -0
  56. package/packages/core/dist/intelligence/decay-engine.d.ts +27 -0
  57. package/packages/core/dist/intelligence/decay-engine.js +190 -0
  58. package/packages/core/dist/intelligence/duplicate-detector.d.ts +20 -0
  59. package/packages/core/dist/intelligence/duplicate-detector.js +55 -0
  60. package/packages/core/dist/intelligence/fsrs.d.ts +43 -0
  61. package/packages/core/dist/intelligence/fsrs.js +70 -0
  62. package/packages/core/dist/intelligence/gap-detector.d.ts +25 -0
  63. package/packages/core/dist/intelligence/gap-detector.js +78 -0
  64. package/packages/core/dist/intelligence/learning-path.d.ts +31 -0
  65. package/packages/core/dist/intelligence/learning-path.js +53 -0
  66. package/packages/core/dist/intelligence/notifications.d.ts +31 -0
  67. package/packages/core/dist/intelligence/notifications.js +65 -0
  68. package/packages/core/dist/intelligence/predictive-gaps.d.ts +14 -0
  69. package/packages/core/dist/intelligence/predictive-gaps.js +74 -0
  70. package/packages/core/dist/intelligence/semantic-versioning.d.ts +37 -0
  71. package/packages/core/dist/intelligence/semantic-versioning.js +68 -0
  72. package/packages/core/dist/intelligence/types.d.ts +28 -0
  73. package/packages/core/dist/intelligence/types.js +3 -0
  74. package/packages/core/dist/mcp/custom-tools.d.ts +29 -0
  75. package/packages/core/dist/mcp/custom-tools.js +70 -0
  76. package/packages/core/{src/mcp/index.ts → dist/mcp/index.d.ts} +1 -0
  77. package/packages/core/dist/mcp/index.js +2 -0
  78. package/packages/core/dist/mcp/server.d.ts +49 -0
  79. package/packages/core/dist/mcp/server.js +133 -0
  80. package/packages/core/dist/mcp/tools/agentic-graph.d.ts +87 -0
  81. package/packages/core/dist/mcp/tools/agentic-graph.js +88 -0
  82. package/packages/core/dist/mcp/tools/brief.d.ts +31 -0
  83. package/packages/core/dist/mcp/tools/brief.js +39 -0
  84. package/packages/core/dist/mcp/tools/decay.d.ts +33 -0
  85. package/packages/core/dist/mcp/tools/decay.js +32 -0
  86. package/packages/core/dist/mcp/tools/decision-journal.d.ts +78 -0
  87. package/packages/core/dist/mcp/tools/decision-journal.js +79 -0
  88. package/packages/core/dist/mcp/tools/export.d.ts +29 -0
  89. package/packages/core/dist/mcp/tools/export.js +60 -0
  90. package/packages/core/dist/mcp/tools/federated-search.d.ts +29 -0
  91. package/packages/core/dist/mcp/tools/federated-search.js +36 -0
  92. package/packages/core/dist/mcp/tools/generate-claude-md.d.ts +35 -0
  93. package/packages/core/dist/mcp/tools/generate-claude-md.js +107 -0
  94. package/packages/core/dist/mcp/tools/get-document.d.ts +35 -0
  95. package/packages/core/dist/mcp/tools/get-document.js +25 -0
  96. package/packages/core/dist/mcp/tools/get-related.d.ts +32 -0
  97. package/packages/core/dist/mcp/tools/get-related.js +33 -0
  98. package/packages/core/dist/mcp/tools/learning-path.d.ts +23 -0
  99. package/packages/core/dist/mcp/tools/learning-path.js +45 -0
  100. package/packages/core/dist/mcp/tools/list-topics.d.ts +15 -0
  101. package/packages/core/dist/mcp/tools/list-topics.js +18 -0
  102. package/packages/core/dist/mcp/tools/search.d.ts +39 -0
  103. package/packages/core/dist/mcp/tools/search.js +29 -0
  104. package/packages/core/dist/mcp/tools/snapshot.d.ts +47 -0
  105. package/packages/core/dist/mcp/tools/snapshot.js +84 -0
  106. package/packages/core/dist/multi-vault/index.d.ts +26 -0
  107. package/packages/core/dist/multi-vault/index.js +80 -0
  108. package/packages/core/dist/pack/creator.d.ts +21 -0
  109. package/packages/core/dist/pack/creator.js +105 -0
  110. package/packages/core/dist/pack/exporter.d.ts +4 -0
  111. package/packages/core/dist/pack/exporter.js +18 -0
  112. package/packages/core/dist/pack/importer.d.ts +10 -0
  113. package/packages/core/dist/pack/importer.js +55 -0
  114. package/packages/core/{src/pack/index.ts → dist/pack/index.d.ts} +1 -0
  115. package/packages/core/dist/pack/index.js +5 -0
  116. package/packages/core/dist/pack/marketplace.d.ts +14 -0
  117. package/packages/core/dist/pack/marketplace.js +90 -0
  118. package/packages/core/dist/pack/pii-masker.d.ts +7 -0
  119. package/packages/core/dist/pack/pii-masker.js +29 -0
  120. package/packages/core/dist/pack/types.d.ts +36 -0
  121. package/packages/core/dist/pack/types.js +3 -0
  122. package/packages/core/dist/plugins/index.d.ts +35 -0
  123. package/packages/core/dist/plugins/index.js +57 -0
  124. package/packages/core/dist/plugins/webhooks.d.ts +30 -0
  125. package/packages/core/dist/plugins/webhooks.js +79 -0
  126. package/packages/core/dist/search/bm25.d.ts +4 -0
  127. package/packages/core/dist/search/bm25.js +10 -0
  128. package/packages/core/dist/search/index.d.ts +13 -0
  129. package/packages/core/dist/search/index.js +63 -0
  130. package/packages/core/dist/search/rrf.d.ts +7 -0
  131. package/packages/core/dist/search/rrf.js +21 -0
  132. package/packages/core/dist/search/semantic.d.ts +5 -0
  133. package/packages/core/dist/search/semantic.js +6 -0
  134. package/packages/core/{src/store/index.ts → dist/store/index.d.ts} +1 -0
  135. package/packages/core/dist/store/index.js +2 -0
  136. package/packages/core/dist/store/sqlite-vec.d.ts +6 -0
  137. package/packages/core/dist/store/sqlite-vec.js +251 -0
  138. package/packages/core/dist/store/types.d.ts +20 -0
  139. package/packages/core/dist/store/types.js +3 -0
  140. package/packages/core/dist/team/index.d.ts +25 -0
  141. package/packages/core/dist/team/index.js +97 -0
  142. package/packages/core/dist/types/chunk.d.ts +23 -0
  143. package/packages/core/dist/types/chunk.js +3 -0
  144. package/packages/core/dist/types/document.d.ts +23 -0
  145. package/packages/core/dist/types/document.js +3 -0
  146. package/packages/core/dist/types/graph.d.ts +39 -0
  147. package/packages/core/dist/types/graph.js +3 -0
  148. package/packages/core/dist/types/index.d.ts +5 -0
  149. package/packages/core/dist/types/index.js +2 -0
  150. package/packages/core/dist/types/search.d.ts +39 -0
  151. package/packages/core/dist/types/search.js +3 -0
  152. package/packages/core/dist/utils/retry.d.ts +25 -0
  153. package/packages/core/dist/utils/retry.js +59 -0
  154. package/.github/workflows/pages.yml +0 -37
  155. package/memory/MEMORY.md +0 -25
  156. package/packages/cli/dist/commands/brief-cmd.d.ts.map +0 -1
  157. package/packages/cli/dist/commands/brief-cmd.js.map +0 -1
  158. package/packages/cli/dist/commands/capture-cmd.d.ts.map +0 -1
  159. package/packages/cli/dist/commands/capture-cmd.js.map +0 -1
  160. package/packages/cli/dist/commands/card-cmd.d.ts.map +0 -1
  161. package/packages/cli/dist/commands/card-cmd.js.map +0 -1
  162. package/packages/cli/dist/commands/clip-cmd.d.ts.map +0 -1
  163. package/packages/cli/dist/commands/clip-cmd.js.map +0 -1
  164. package/packages/cli/dist/commands/cloud-cmd.d.ts.map +0 -1
  165. package/packages/cli/dist/commands/cloud-cmd.js.map +0 -1
  166. package/packages/cli/dist/commands/contradictions-cmd.d.ts.map +0 -1
  167. package/packages/cli/dist/commands/contradictions-cmd.js.map +0 -1
  168. package/packages/cli/dist/commands/decay-cmd.d.ts.map +0 -1
  169. package/packages/cli/dist/commands/decay-cmd.js.map +0 -1
  170. package/packages/cli/dist/commands/digest-cmd.d.ts.map +0 -1
  171. package/packages/cli/dist/commands/digest-cmd.js.map +0 -1
  172. package/packages/cli/dist/commands/duplicates-cmd.d.ts.map +0 -1
  173. package/packages/cli/dist/commands/duplicates-cmd.js.map +0 -1
  174. package/packages/cli/dist/commands/federate-cmd.d.ts.map +0 -1
  175. package/packages/cli/dist/commands/federate-cmd.js.map +0 -1
  176. package/packages/cli/dist/commands/gaps-cmd.d.ts.map +0 -1
  177. package/packages/cli/dist/commands/gaps-cmd.js.map +0 -1
  178. package/packages/cli/dist/commands/graph-cmd.d.ts.map +0 -1
  179. package/packages/cli/dist/commands/graph-cmd.js.map +0 -1
  180. package/packages/cli/dist/commands/index-cmd.d.ts.map +0 -1
  181. package/packages/cli/dist/commands/index-cmd.js.map +0 -1
  182. package/packages/cli/dist/commands/init-cmd.d.ts.map +0 -1
  183. package/packages/cli/dist/commands/init-cmd.js.map +0 -1
  184. package/packages/cli/dist/commands/learn-cmd.d.ts.map +0 -1
  185. package/packages/cli/dist/commands/learn-cmd.js.map +0 -1
  186. package/packages/cli/dist/commands/pack-cmd.d.ts.map +0 -1
  187. package/packages/cli/dist/commands/pack-cmd.js.map +0 -1
  188. package/packages/cli/dist/commands/review-cmd.d.ts.map +0 -1
  189. package/packages/cli/dist/commands/review-cmd.js.map +0 -1
  190. package/packages/cli/dist/commands/search-cmd.d.ts.map +0 -1
  191. package/packages/cli/dist/commands/search-cmd.js.map +0 -1
  192. package/packages/cli/dist/commands/serve-cmd.d.ts.map +0 -1
  193. package/packages/cli/dist/commands/serve-cmd.js.map +0 -1
  194. package/packages/cli/dist/commands/status-cmd.d.ts.map +0 -1
  195. package/packages/cli/dist/commands/status-cmd.js.map +0 -1
  196. package/packages/cli/dist/commands/sync-cmd.d.ts.map +0 -1
  197. package/packages/cli/dist/commands/sync-cmd.js.map +0 -1
  198. package/packages/cli/dist/commands/vault-cmd.d.ts.map +0 -1
  199. package/packages/cli/dist/commands/vault-cmd.js.map +0 -1
  200. package/packages/cli/dist/index.d.ts.map +0 -1
  201. package/packages/cli/dist/index.js.map +0 -1
  202. package/packages/cli/src/commands/brief-cmd.ts +0 -87
  203. package/packages/cli/src/commands/capture-cmd.ts +0 -34
  204. package/packages/cli/src/commands/card-cmd.ts +0 -29
  205. package/packages/cli/src/commands/clip-cmd.ts +0 -172
  206. package/packages/cli/src/commands/cloud-cmd.ts +0 -75
  207. package/packages/cli/src/commands/contradictions-cmd.ts +0 -41
  208. package/packages/cli/src/commands/decay-cmd.ts +0 -57
  209. package/packages/cli/src/commands/digest-cmd.ts +0 -89
  210. package/packages/cli/src/commands/duplicates-cmd.ts +0 -38
  211. package/packages/cli/src/commands/federate-cmd.ts +0 -256
  212. package/packages/cli/src/commands/gaps-cmd.ts +0 -40
  213. package/packages/cli/src/commands/graph-cmd.ts +0 -88
  214. package/packages/cli/src/commands/index-cmd.ts +0 -65
  215. package/packages/cli/src/commands/init-cmd.ts +0 -145
  216. package/packages/cli/src/commands/learn-cmd.ts +0 -56
  217. package/packages/cli/src/commands/pack-cmd.ts +0 -121
  218. package/packages/cli/src/commands/review-cmd.ts +0 -125
  219. package/packages/cli/src/commands/search-cmd.ts +0 -45
  220. package/packages/cli/src/commands/serve-cmd.ts +0 -17
  221. package/packages/cli/src/commands/status-cmd.ts +0 -37
  222. package/packages/cli/src/commands/sync-cmd.ts +0 -68
  223. package/packages/cli/src/commands/vault-cmd.ts +0 -64
  224. package/packages/cli/src/index.ts +0 -187
  225. package/packages/core/src/api/graph-data.ts +0 -286
  226. package/packages/core/src/api/server.ts +0 -660
  227. package/packages/core/src/capture/voice.ts +0 -168
  228. package/packages/core/src/cloud/sync.ts +0 -167
  229. package/packages/core/src/config.ts +0 -82
  230. package/packages/core/src/federation/credits.ts +0 -80
  231. package/packages/core/src/federation/hyperswarm.d.ts +0 -19
  232. package/packages/core/src/federation/identity.ts +0 -90
  233. package/packages/core/src/federation/node.ts +0 -235
  234. package/packages/core/src/federation/privacy.ts +0 -52
  235. package/packages/core/src/federation/reputation.ts +0 -202
  236. package/packages/core/src/federation/search.ts +0 -129
  237. package/packages/core/src/federation/sharing.ts +0 -315
  238. package/packages/core/src/federation/trust.ts +0 -76
  239. package/packages/core/src/federation/types.ts +0 -25
  240. package/packages/core/src/i18n/index.ts +0 -85
  241. package/packages/core/src/indexer/chunker.ts +0 -180
  242. package/packages/core/src/indexer/embedder.ts +0 -9
  243. package/packages/core/src/indexer/index.ts +0 -113
  244. package/packages/core/src/indexer/local-embedder.ts +0 -35
  245. package/packages/core/src/indexer/scanner.ts +0 -142
  246. package/packages/core/src/indexer/watcher.ts +0 -62
  247. package/packages/core/src/intelligence/contradiction-detector.ts +0 -134
  248. package/packages/core/src/intelligence/decay-engine.ts +0 -229
  249. package/packages/core/src/intelligence/duplicate-detector.ts +0 -71
  250. package/packages/core/src/intelligence/fsrs.ts +0 -79
  251. package/packages/core/src/intelligence/gap-detector.ts +0 -109
  252. package/packages/core/src/intelligence/learning-path.ts +0 -86
  253. package/packages/core/src/intelligence/notifications.ts +0 -106
  254. package/packages/core/src/intelligence/predictive-gaps.ts +0 -94
  255. package/packages/core/src/intelligence/semantic-versioning.ts +0 -97
  256. package/packages/core/src/intelligence/types.ts +0 -28
  257. package/packages/core/src/mcp/custom-tools.ts +0 -97
  258. package/packages/core/src/mcp/server.ts +0 -142
  259. package/packages/core/src/mcp/tools/agentic-graph.ts +0 -96
  260. package/packages/core/src/mcp/tools/brief.ts +0 -49
  261. package/packages/core/src/mcp/tools/decay.ts +0 -40
  262. package/packages/core/src/mcp/tools/decision-journal.ts +0 -95
  263. package/packages/core/src/mcp/tools/export.ts +0 -72
  264. package/packages/core/src/mcp/tools/federated-search.ts +0 -43
  265. package/packages/core/src/mcp/tools/generate-claude-md.ts +0 -130
  266. package/packages/core/src/mcp/tools/get-document.ts +0 -26
  267. package/packages/core/src/mcp/tools/get-related.ts +0 -41
  268. package/packages/core/src/mcp/tools/learning-path.ts +0 -52
  269. package/packages/core/src/mcp/tools/list-topics.ts +0 -20
  270. package/packages/core/src/mcp/tools/search.ts +0 -35
  271. package/packages/core/src/mcp/tools/snapshot.ts +0 -98
  272. package/packages/core/src/multi-vault/index.ts +0 -118
  273. package/packages/core/src/pack/creator.ts +0 -127
  274. package/packages/core/src/pack/exporter.ts +0 -21
  275. package/packages/core/src/pack/importer.ts +0 -82
  276. package/packages/core/src/pack/marketplace.ts +0 -103
  277. package/packages/core/src/pack/pii-masker.ts +0 -38
  278. package/packages/core/src/pack/types.ts +0 -39
  279. package/packages/core/src/plugins/index.ts +0 -100
  280. package/packages/core/src/plugins/webhooks.ts +0 -110
  281. package/packages/core/src/search/bm25.ts +0 -16
  282. package/packages/core/src/search/index.ts +0 -83
  283. package/packages/core/src/search/rrf.ts +0 -31
  284. package/packages/core/src/search/semantic.ts +0 -15
  285. package/packages/core/src/store/sqlite-vec.ts +0 -290
  286. package/packages/core/src/store/types.ts +0 -22
  287. package/packages/core/src/team/index.ts +0 -126
  288. package/packages/core/src/types/chunk.ts +0 -25
  289. package/packages/core/src/types/document.ts +0 -24
  290. package/packages/core/src/types/graph.ts +0 -44
  291. package/packages/core/src/types/index.ts +0 -15
  292. package/packages/core/src/types/search.ts +0 -38
  293. package/packages/core/src/utils/retry.ts +0 -85
  294. package/packages/core/tests/api-card.test.ts +0 -60
  295. package/packages/core/tests/api-routes.test.ts +0 -98
  296. package/packages/core/tests/bm25.test.ts +0 -87
  297. package/packages/core/tests/chunker.test.ts +0 -48
  298. package/packages/core/tests/cluster.test.ts +0 -75
  299. package/packages/core/tests/constellation.test.ts +0 -77
  300. package/packages/core/tests/export-utils.test.ts +0 -97
  301. package/packages/core/tests/fsrs.test.ts +0 -96
  302. package/packages/core/tests/gesture-detector.test.ts +0 -45
  303. package/packages/core/tests/graph-data.test.ts +0 -87
  304. package/packages/core/tests/layout.test.ts +0 -83
  305. package/packages/core/tests/mcp.test.ts +0 -148
  306. package/packages/core/tests/pack.test.ts +0 -127
  307. package/packages/core/tests/pii-masker.test.ts +0 -42
  308. package/packages/core/tests/profile-card.test.ts +0 -62
  309. package/packages/core/tests/rrf.test.ts +0 -29
  310. package/packages/core/tests/search-integration.test.ts +0 -139
  311. package/packages/core/tests/store.test.ts +0 -80
  312. package/packages/graph/click-result.png +0 -0
  313. package/packages/graph/dist/assets/camera_utils-BMxqtvoZ.js +0 -1
  314. package/packages/graph/dist/assets/hands-DXA01_mx.js +0 -18
  315. package/packages/graph/dist/assets/index-DMEe2diW.js +0 -4192
  316. package/packages/graph/dist/assets/layout.worker-DbKCEFTz.js +0 -1
  317. package/packages/graph/dist/index.html +0 -17
  318. package/packages/graph/index.html +0 -17
  319. package/packages/graph/package.json +0 -32
  320. package/packages/graph/src/App.tsx +0 -7
  321. package/packages/graph/src/api/client.ts +0 -39
  322. package/packages/graph/src/components/ClusterFilter.tsx +0 -73
  323. package/packages/graph/src/components/ConstellationView.tsx +0 -232
  324. package/packages/graph/src/components/ExportPanel.tsx +0 -177
  325. package/packages/graph/src/components/Graph3D.tsx +0 -230
  326. package/packages/graph/src/components/GraphEdges.tsx +0 -100
  327. package/packages/graph/src/components/GraphNodes.tsx +0 -386
  328. package/packages/graph/src/components/HealthDashboard.tsx +0 -173
  329. package/packages/graph/src/components/Layout.tsx +0 -214
  330. package/packages/graph/src/components/MotionOverlay.tsx +0 -81
  331. package/packages/graph/src/components/MotionToggle.tsx +0 -33
  332. package/packages/graph/src/components/MultiverseView.tsx +0 -286
  333. package/packages/graph/src/components/NodeDetail.tsx +0 -232
  334. package/packages/graph/src/components/PulseParticle.tsx +0 -232
  335. package/packages/graph/src/components/SearchBar.tsx +0 -107
  336. package/packages/graph/src/components/StarField.tsx +0 -197
  337. package/packages/graph/src/components/StatusBar.tsx +0 -53
  338. package/packages/graph/src/components/Timeline.tsx +0 -148
  339. package/packages/graph/src/components/ToolsPanel.tsx +0 -512
  340. package/packages/graph/src/components/Tooltip.tsx +0 -100
  341. package/packages/graph/src/components/TypeFilter.tsx +0 -131
  342. package/packages/graph/src/embed/EmbedGraph.tsx +0 -144
  343. package/packages/graph/src/hooks/useConstellationLOD.ts +0 -76
  344. package/packages/graph/src/hooks/useDecay.ts +0 -37
  345. package/packages/graph/src/hooks/useExport.ts +0 -165
  346. package/packages/graph/src/hooks/useGraph.ts +0 -69
  347. package/packages/graph/src/hooks/useKeyboardNav.ts +0 -122
  348. package/packages/graph/src/hooks/useLayout.ts +0 -45
  349. package/packages/graph/src/hooks/useMotion.ts +0 -120
  350. package/packages/graph/src/hooks/usePulse.ts +0 -58
  351. package/packages/graph/src/hooks/useSearch.ts +0 -71
  352. package/packages/graph/src/lib/constellation.ts +0 -107
  353. package/packages/graph/src/lib/export-utils.ts +0 -48
  354. package/packages/graph/src/lib/gesture-detector.ts +0 -123
  355. package/packages/graph/src/lib/layout.worker.ts +0 -153
  356. package/packages/graph/src/lib/motion-controller.ts +0 -83
  357. package/packages/graph/src/lib/profile-card.ts +0 -122
  358. package/packages/graph/src/main.tsx +0 -4
  359. package/packages/graph/src/stores/graph-store.ts +0 -155
  360. package/packages/graph/success.png +0 -0
  361. package/packages/graph/test-click.mjs +0 -49
  362. package/packages/graph/test-explore.mjs +0 -102
  363. package/packages/graph/test-final.mjs +0 -61
  364. package/packages/graph/test-graph.mjs +0 -139
  365. package/packages/graph/test-hover.mjs +0 -48
  366. package/packages/graph/test-pulse.mjs +0 -68
  367. package/packages/graph/test-screenshot.mjs +0 -56
  368. package/packages/graph/test-v2.mjs +0 -97
  369. package/packages/graph/tsconfig.tsbuildinfo +0 -1
  370. package/packages/graph/vite.config.ts +0 -15
  371. package/packages/sync/.env.example +0 -11
  372. package/packages/sync/.sync-state.json +0 -317
  373. package/packages/sync/.upload-state.json +0 -1009
  374. package/packages/sync/create-stella-network-notion.mjs +0 -151
  375. package/packages/sync/create-stellavault-project-notion.mjs +0 -322
  376. package/packages/sync/logs/sync-2026-03-28.log +0 -6
  377. package/packages/sync/logs/sync-2026-03-29.log +0 -12
  378. package/packages/sync/logs/sync-2026-03-30.log +0 -6
  379. package/packages/sync/logs/sync-2026-03-31.log +0 -6
  380. package/packages/sync/logs/sync-2026-04-01.log +0 -6
  381. package/packages/sync/logs/sync-2026-04-02.log +0 -6
  382. package/packages/sync/package-lock.json +0 -373
  383. package/packages/sync/package.json +0 -16
  384. package/packages/sync/run-sync.bat +0 -18
  385. package/packages/sync/run-sync.mjs +0 -46
  386. package/packages/sync/setup-scheduler.mjs +0 -119
  387. package/packages/sync/structured-sync.mjs +0 -187
  388. package/packages/sync/sync-to-obsidian.mjs +0 -264
  389. package/packages/sync/upload-pdca-to-notion.mjs +0 -495
  390. package/tsconfig.base.json +0 -18
@@ -1,235 +0,0 @@
1
- // Design Ref: §4 — FederationNode (Hyperswarm P2P)
2
- // Plan SC: SC1 (2노드 연결), SC5 (오프라인 정상)
3
-
4
- import { createHash } from 'node:crypto';
5
- import { EventEmitter } from 'node:events';
6
- import { getOrCreateIdentity, type NodeIdentity } from './identity.js';
7
- import type { PeerInfo, FederationMessage } from './types.js';
8
-
9
- const FEDERATION_TOPIC = createHash('sha256').update('stellavault-federation-v1').digest();
10
-
11
- export class FederationNode extends EventEmitter {
12
- private swarm: any = null;
13
- private identity: NodeIdentity;
14
- private peers = new Map<string, { info: PeerInfo; conn: any }>();
15
- private running = false;
16
- private documentCount = 0;
17
- private topTopics: string[] = [];
18
-
19
- constructor(displayName?: string) {
20
- super();
21
- this.identity = getOrCreateIdentity(displayName);
22
- }
23
-
24
- get peerId(): string { return this.identity.peerId; }
25
- get displayName(): string { return this.identity.displayName; }
26
- get peerCount(): number { return this.peers.size; }
27
- get isRunning(): boolean { return this.running; }
28
-
29
- setLocalStats(documentCount: number, topTopics: string[]) {
30
- this.documentCount = documentCount;
31
- this.topTopics = topTopics.slice(0, 5);
32
- }
33
-
34
- // Design Ref: §4 — join()
35
- async join(): Promise<void> {
36
- if (this.running) return;
37
-
38
- const Hyperswarm = (await import('hyperswarm')).default;
39
- this.swarm = new Hyperswarm({ maxPeers: 50 });
40
-
41
- this.swarm.on('connection', (conn: any, _info: any) => {
42
- this.handleConnection(conn);
43
- });
44
-
45
- const discovery = this.swarm.join(FEDERATION_TOPIC, { server: true, client: true });
46
- await discovery.flushed();
47
-
48
- this.running = true;
49
- this.emit('joined', { peerId: this.peerId, topic: FEDERATION_TOPIC.toString('hex').slice(0, 16) });
50
- }
51
-
52
- // Design Ref: §4 — joinDirect() 수동 IP 폴백
53
- async joinDirect(host: string, port: number): Promise<void> {
54
- const net = await import('node:net');
55
- const conn = net.connect(port, host);
56
-
57
- await new Promise<void>((resolve, reject) => {
58
- conn.on('connect', () => {
59
- this.handleConnection(conn);
60
- resolve();
61
- });
62
- conn.on('error', reject);
63
- setTimeout(() => reject(new Error('Connection timeout')), 15000);
64
- });
65
-
66
- if (!this.running) this.running = true;
67
- }
68
-
69
- async leave(): Promise<void> {
70
- if (!this.running) return;
71
-
72
- for (const [, peer] of this.peers) {
73
- try {
74
- this.sendMessage(peer.conn, { type: 'leave', peerId: this.peerId });
75
- peer.conn.end();
76
- } catch { /* ignore */ }
77
- }
78
-
79
- this.peers.clear();
80
- await this.swarm?.destroy();
81
- this.swarm = null;
82
- this.running = false;
83
- this.emit('left');
84
- }
85
-
86
- getPeers(): PeerInfo[] {
87
- return [...this.peers.values()].map(p => p.info);
88
- }
89
-
90
- // 피어에게 검색 쿼리 전송 (FederatedSearch에서 사용)
91
- sendSearchQuery(peerId: string, queryId: string, embedding: number[], limit: number): void {
92
- const peer = this.peers.get(peerId);
93
- if (!peer) return;
94
- this.sendMessage(peer.conn, { type: 'search_query', queryId, embedding, limit });
95
- }
96
-
97
- // 피어에게 검색 결과 응답 (FederatedSearch에서 사용)
98
- sendSearchResult(peerId: string, queryId: string, results: Array<{ title: string; similarity: number; snippet: string }>): void {
99
- const peer = this.peers.get(peerId);
100
- if (!peer) return;
101
- this.sendMessage(peer.conn, { type: 'search_result', queryId, results });
102
- }
103
-
104
- // --- Private ---
105
-
106
- private handleConnection(conn: any) {
107
- // 핸드셰이크 전송
108
- this.sendMessage(conn, {
109
- type: 'handshake',
110
- peerId: this.peerId,
111
- displayName: this.identity.displayName,
112
- version: '0.1.0',
113
- documentCount: this.documentCount,
114
- topTopics: this.topTopics,
115
- });
116
-
117
- let buffer = '';
118
- const MAX_BUFFER = 1024 * 1024; // HIGH-04: 1MB 버퍼 제한 (OOM 방지)
119
- const MAX_MESSAGE = 64 * 1024; // 개별 메시지 64KB 제한
120
-
121
- conn.on('data', (data: Buffer) => {
122
- buffer += data.toString();
123
-
124
- // 버퍼 크기 초과 시 연결 종료
125
- if (buffer.length > MAX_BUFFER) {
126
- console.error('Federation: buffer overflow from peer, disconnecting');
127
- buffer = '';
128
- conn.end();
129
- return;
130
- }
131
-
132
- const lines = buffer.split('\n');
133
- buffer = lines.pop() ?? '';
134
-
135
- for (const line of lines) {
136
- if (!line.trim()) continue;
137
- if (line.length > MAX_MESSAGE) continue; // 초대형 메시지 무시
138
- try {
139
- const msg: FederationMessage = JSON.parse(line);
140
- this.handleMessage(conn, msg);
141
- } catch { /* malformed — ignore */ }
142
- }
143
- });
144
-
145
- conn.on('close', () => {
146
- for (const [peerId, peer] of this.peers) {
147
- if (peer.conn === conn) {
148
- this.peers.delete(peerId);
149
- this.emit('peer_left', { peerId });
150
- break;
151
- }
152
- }
153
- });
154
-
155
- conn.on('error', () => { /* swallow */ });
156
- }
157
-
158
- // MED: 메시지 스키마 기본 검증
159
- private validateMessage(msg: any): boolean {
160
- if (!msg || typeof msg !== 'object' || typeof msg.type !== 'string') return false;
161
- if (msg.type === 'handshake' && (typeof msg.peerId !== 'string' || typeof msg.displayName !== 'string')) return false;
162
- if (msg.type === 'search_query' && (!Array.isArray(msg.embedding) || msg.embedding.length !== 384)) return false;
163
- if (msg.type === 'search_result' && !Array.isArray(msg.results)) return false;
164
- return true;
165
- }
166
-
167
- private handleMessage(conn: any, msg: FederationMessage) {
168
- if (!this.validateMessage(msg)) return; // 스키마 불일치 메시지 무시
169
-
170
- switch (msg.type) {
171
- case 'handshake': {
172
- // MED: displayName 길이 제한
173
- const safeName = (msg.displayName ?? '').slice(0, 50);
174
- const peerInfo: PeerInfo = {
175
- peerId: msg.peerId,
176
- displayName: safeName,
177
- documentCount: Math.min(msg.documentCount ?? 0, 1000000), // 합리적 상한
178
- topTopics: (msg.topTopics ?? []).slice(0, 10),
179
- joinedAt: new Date().toISOString(),
180
- lastSeen: new Date().toISOString(),
181
- };
182
- this.peers.set(msg.peerId, { info: peerInfo, conn });
183
- this.emit('peer_joined', peerInfo);
184
- break;
185
- }
186
-
187
- case 'search_query': {
188
- // Design Ref: §5 — 검색 요청 수신
189
- this.emit('search_request', {
190
- peerId: msg.queryId, // queryId를 추적용으로 사용
191
- queryId: msg.queryId,
192
- embedding: msg.embedding,
193
- limit: msg.limit,
194
- // respond 함수: 호출 측에서 사용
195
- respondTo: (() => {
196
- // 어느 피어가 보냈는지 찾기
197
- for (const [pid, peer] of this.peers) {
198
- if (peer.conn === conn) return pid;
199
- }
200
- return null;
201
- })(),
202
- });
203
- break;
204
- }
205
-
206
- case 'search_result': {
207
- // FederatedSearch가 이벤트로 수신
208
- this.emit('search_response', {
209
- queryId: msg.queryId,
210
- results: msg.results,
211
- peerId: (() => {
212
- for (const [pid, peer] of this.peers) {
213
- if (peer.conn === conn) return pid;
214
- }
215
- return 'unknown';
216
- })(),
217
- });
218
- break;
219
- }
220
-
221
- case 'leave': {
222
- this.peers.delete(msg.peerId);
223
- this.emit('peer_left', { peerId: msg.peerId });
224
- break;
225
- }
226
- }
227
- }
228
-
229
- // Design Ref: §7 — JSON + newline delimiter
230
- private sendMessage(conn: any, msg: FederationMessage) {
231
- try {
232
- conn.write(JSON.stringify(msg) + '\n');
233
- } catch { /* connection may be closed */ }
234
- }
235
- }
@@ -1,52 +0,0 @@
1
- // Federation Phase 2: Differential Privacy
2
- // 임베딩 벡터에 노이즈를 추가하여 원문 복원 방지
3
-
4
- import { randomBytes } from 'node:crypto';
5
-
6
- export interface DPConfig {
7
- epsilon: number; // 프라이버시 예산 (낮을수록 더 안전, 기본 1.0)
8
- enabled: boolean;
9
- }
10
-
11
- const DEFAULT_DP: DPConfig = { epsilon: 1.0, enabled: true };
12
-
13
- // 가우시안 노이즈 생성 (Box-Muller 변환)
14
- function gaussianNoise(): number {
15
- const u1 = Math.max(1e-10, Math.random());
16
- const u2 = Math.random();
17
- return Math.sqrt(-2 * Math.log(u1)) * Math.cos(2 * Math.PI * u2);
18
- }
19
-
20
- // 임베딩 벡터에 Differential Privacy 노이즈 추가
21
- export function addDPNoise(embedding: number[], config: DPConfig = DEFAULT_DP): number[] {
22
- if (!config.enabled) return embedding;
23
-
24
- const sensitivity = 1.0; // L2 sensitivity (normalized embeddings)
25
- const sigma = sensitivity / config.epsilon;
26
-
27
- return embedding.map(v => v + gaussianNoise() * sigma);
28
- }
29
-
30
- // 노이즈 추가 후 L2 정규화 (코사인 유사도 유지)
31
- export function addDPNoiseNormalized(embedding: number[], config: DPConfig = DEFAULT_DP): number[] {
32
- const noisy = addDPNoise(embedding, config);
33
-
34
- // L2 정규화
35
- let norm = 0;
36
- for (const v of noisy) norm += v * v;
37
- norm = Math.sqrt(norm);
38
- if (norm === 0) return noisy;
39
-
40
- return noisy.map(v => v / norm);
41
- }
42
-
43
- // 스니펫에 DP 적용 (단어 단위 마스킹)
44
- export function maskSnippet(snippet: string, maskRate = 0.3): string {
45
- const words = snippet.split(/\s+/);
46
- return words.map(w => {
47
- if (Math.random() < maskRate && w.length > 2) {
48
- return w[0] + '***';
49
- }
50
- return w;
51
- }).join(' ');
52
- }
@@ -1,202 +0,0 @@
1
- // Federation: Node Reputation System
2
- // 자동 평판 점수 — trust + consistency + freshness + consensus + history
3
-
4
- import { readFileSync, writeFileSync, existsSync, mkdirSync } from 'node:fs';
5
- import { join } from 'node:path';
6
- import { homedir } from 'node:os';
7
- import { getTrustLevel } from './trust.js';
8
-
9
- export interface ReputationRecord {
10
- peerId: string;
11
- displayName: string;
12
-
13
- // 수동 (Web of Trust)
14
- trustBase: number; // vouch=30, neutral=0, block=-100
15
-
16
- // 자동: 결과 일관성
17
- consistencyScore: number; // 0-25, 다른 노드들과 결과 유사도
18
- consistencySamples: number; // 측정 횟수
19
-
20
- // 자동: 활동 빈도
21
- freshnessScore: number; // 0-15, 최근 활동
22
- lastSeen: string;
23
- totalInteractions: number;
24
-
25
- // 자동: 합의
26
- consensusScore: number; // 0-20, 같은 쿼리에 다른 노드와 동일 결과
27
- consensusSamples: number;
28
-
29
- // 자동: 유용성 피드백
30
- historyScore: number; // 0-10, 사용자 피드백 (결과 클릭율 등)
31
- helpfulCount: number;
32
- unhelpfulCount: number;
33
-
34
- updatedAt: string;
35
- }
36
-
37
- const REP_FILE = join(homedir(), '.stellavault', 'federation', 'reputation.json');
38
-
39
- function loadRepDb(): Map<string, ReputationRecord> {
40
- if (!existsSync(REP_FILE)) return new Map();
41
- const records = JSON.parse(readFileSync(REP_FILE, 'utf-8')) as ReputationRecord[];
42
- return new Map(records.map(r => [r.peerId, r]));
43
- }
44
-
45
- function saveRepDb(db: Map<string, ReputationRecord>): void {
46
- mkdirSync(join(homedir(), '.stellavault', 'federation'), { recursive: true });
47
- writeFileSync(REP_FILE, JSON.stringify([...db.values()], null, 2), 'utf-8');
48
- }
49
-
50
- function getOrCreateRecord(peerId: string, displayName = ''): ReputationRecord {
51
- const db = loadRepDb();
52
- if (db.has(peerId)) return db.get(peerId)!;
53
- return {
54
- peerId, displayName,
55
- trustBase: 0,
56
- consistencyScore: 0, consistencySamples: 0,
57
- freshnessScore: 0, lastSeen: new Date().toISOString(), totalInteractions: 0,
58
- consensusScore: 0, consensusSamples: 0,
59
- historyScore: 0, helpfulCount: 0, unhelpfulCount: 0,
60
- updatedAt: new Date().toISOString(),
61
- };
62
- }
63
-
64
- // 종합 평판 점수 계산 (0-100)
65
- export function computeReputation(peerId: string): number {
66
- const rec = getOrCreateRecord(peerId);
67
-
68
- // 수동 신뢰 기반
69
- const trustLevel = getTrustLevel(peerId);
70
- const trustBase = trustLevel === 'vouched' ? 30 : trustLevel === 'blocked' ? -100 : 0;
71
-
72
- // blocked이면 즉시 0
73
- if (trustBase <= -100) return 0;
74
-
75
- const score = Math.max(0, Math.min(100,
76
- trustBase +
77
- rec.consistencyScore +
78
- rec.freshnessScore +
79
- rec.consensusScore +
80
- rec.historyScore +
81
- // 새 노드 보너스 (상호작용 적으면 중립 시작)
82
- (rec.totalInteractions < 5 ? 40 : 0)
83
- ));
84
-
85
- return Math.round(score);
86
- }
87
-
88
- // 검색 결과에 합의 검증
89
- export function verifyConsensus(
90
- queryId: string,
91
- allResults: Array<{ peerId: string; title: string; similarity: number }>,
92
- ): Map<string, number> {
93
- // 같은 제목을 반환한 노드가 많을수록 → 합의 높음
94
- const titleCounts = new Map<string, number>();
95
- for (const r of allResults) {
96
- titleCounts.set(r.title, (titleCounts.get(r.title) ?? 0) + 1);
97
- }
98
-
99
- const totalPeers = new Set(allResults.map(r => r.peerId)).size;
100
- const consensusBoost = new Map<string, number>();
101
-
102
- for (const r of allResults) {
103
- const count = titleCounts.get(r.title) ?? 1;
104
- // 여러 노드가 같은 결과 → 신뢰도 부스트
105
- const boost = count > 1 ? Math.min((count / totalPeers) * 20, 20) : 0;
106
- const current = consensusBoost.get(r.peerId) ?? 0;
107
- consensusBoost.set(r.peerId, Math.max(current, boost));
108
- }
109
-
110
- return consensusBoost;
111
- }
112
-
113
- // 노드 상호작용 기록 (검색 응답 받을 때마다)
114
- export function recordInteraction(peerId: string, displayName: string): void {
115
- const db = loadRepDb();
116
- const rec = getOrCreateRecord(peerId, displayName);
117
-
118
- rec.totalInteractions++;
119
- rec.lastSeen = new Date().toISOString();
120
- rec.displayName = displayName || rec.displayName;
121
-
122
- // Freshness: 최근 7일 이내 활동이면 만점
123
- const daysSinceLastSeen = (Date.now() - new Date(rec.lastSeen).getTime()) / 86400000;
124
- rec.freshnessScore = daysSinceLastSeen < 1 ? 15 : daysSinceLastSeen < 7 ? 10 : daysSinceLastSeen < 30 ? 5 : 0;
125
-
126
- rec.updatedAt = new Date().toISOString();
127
- db.set(peerId, rec);
128
- saveRepDb(db);
129
- }
130
-
131
- // 결과 일관성 업데이트 (다른 노드와 비교)
132
- export function recordConsistency(peerId: string, matchRate: number): void {
133
- const db = loadRepDb();
134
- const rec = getOrCreateRecord(peerId);
135
-
136
- rec.consistencySamples++;
137
- // 이동 평균
138
- rec.consistencyScore = Math.round(
139
- (rec.consistencyScore * (rec.consistencySamples - 1) + matchRate * 25) / rec.consistencySamples
140
- );
141
-
142
- rec.updatedAt = new Date().toISOString();
143
- db.set(peerId, rec);
144
- saveRepDb(db);
145
- }
146
-
147
- // 사용자 피드백 (결과가 유용했는지)
148
- export function recordFeedback(peerId: string, helpful: boolean): void {
149
- const db = loadRepDb();
150
- const rec = getOrCreateRecord(peerId);
151
-
152
- if (helpful) rec.helpfulCount++;
153
- else rec.unhelpfulCount++;
154
-
155
- const total = rec.helpfulCount + rec.unhelpfulCount;
156
- rec.historyScore = total > 0 ? Math.round((rec.helpfulCount / total) * 10) : 0;
157
-
158
- rec.updatedAt = new Date().toISOString();
159
- db.set(peerId, rec);
160
- saveRepDb(db);
161
- }
162
-
163
- // 합의 점수 업데이트
164
- export function recordConsensus(peerId: string, consensusBoost: number): void {
165
- const db = loadRepDb();
166
- const rec = getOrCreateRecord(peerId);
167
-
168
- rec.consensusSamples++;
169
- rec.consensusScore = Math.round(
170
- (rec.consensusScore * (rec.consensusSamples - 1) + consensusBoost) / rec.consensusSamples
171
- );
172
-
173
- rec.updatedAt = new Date().toISOString();
174
- db.set(peerId, rec);
175
- saveRepDb(db);
176
- }
177
-
178
- // 평판 목록 조회
179
- export function getReputationBoard(): Array<ReputationRecord & { reputation: number }> {
180
- const db = loadRepDb();
181
- return [...db.values()]
182
- .map(r => ({ ...r, reputation: computeReputation(r.peerId) }))
183
- .sort((a, b) => b.reputation - a.reputation);
184
- }
185
-
186
- // 검색 결과 필터 + 정렬 (평판 가중)
187
- export function filterByReputation<T extends { peerId: string; similarity: number }>(
188
- results: T[],
189
- minReputation = 10,
190
- ): (T & { adjustedScore: number; reputation: number })[] {
191
- return results
192
- .map(r => {
193
- const rep = computeReputation(r.peerId);
194
- // blocked 노드 필터링
195
- if (rep === 0) return null;
196
- // 평판 가중 점수: similarity * 0.7 + reputation/100 * 0.3
197
- const adjustedScore = r.similarity * 0.7 + (rep / 100) * 0.3;
198
- return { ...r, adjustedScore, reputation: rep };
199
- })
200
- .filter((r): r is NonNullable<typeof r> => r !== null && r.reputation >= minReputation)
201
- .sort((a, b) => b.adjustedScore - a.adjustedScore);
202
- }
@@ -1,129 +0,0 @@
1
- // Design Ref: §5 — FederatedSearch (피어 검색 + 결과 병합)
2
- // Plan SC: SC2 (연합 검색), SC3 (원문 비노출), SC4 (3초 이내)
3
-
4
- import { randomUUID } from 'node:crypto';
5
- import type { FederationNode } from './node.js';
6
- import type { VectorStore } from '../store/types.js';
7
- import type { Embedder } from '../indexer/embedder.js';
8
- import type { FederatedSearchResult } from './types.js';
9
- import { maskSnippet } from './privacy.js';
10
- import { isDocumentShareable, sanitizeSnippet } from './sharing.js';
11
-
12
- export interface FederatedSearchOptions {
13
- limit?: number;
14
- timeout?: number; // ms, default 5000
15
- }
16
-
17
- export class FederatedSearch {
18
- private additionalStores: VectorStore[] = [];
19
-
20
- constructor(
21
- private node: FederationNode,
22
- private store: VectorStore,
23
- private embedder: Embedder,
24
- ) {}
25
-
26
- // Multi-vault: 추가 store 등록 (Federation 검색 응답 시 전체 vault 검색)
27
- addStore(store: VectorStore): void {
28
- this.additionalStores.push(store);
29
- }
30
-
31
- // Design Ref: §5 — search() 요청 측
32
- async search(query: string, options: FederatedSearchOptions = {}): Promise<FederatedSearchResult[]> {
33
- const { limit = 5, timeout = 5000 } = options;
34
- const peers = this.node.getPeers();
35
-
36
- if (peers.length === 0) {
37
- return [];
38
- }
39
-
40
- // 1. 쿼리 임베딩 생성
41
- const embedding = await this.embedder.embed(query);
42
- const queryId = randomUUID().slice(0, 8);
43
-
44
- // 2. 모든 피어에 병렬 전송 + 응답 대기
45
- const results: FederatedSearchResult[] = [];
46
- const peerMap = new Map(peers.map(p => [p.peerId, p.displayName]));
47
-
48
- const responsePromises = peers.map((peer) => {
49
- return new Promise<void>((resolve) => {
50
- const timer = setTimeout(resolve, timeout);
51
-
52
- const handler = (data: { queryId: string; results: any[]; peerId: string }) => {
53
- if (data.queryId !== queryId) return;
54
-
55
- for (const r of data.results) {
56
- results.push({
57
- title: r.title,
58
- similarity: r.similarity,
59
- snippet: r.snippet,
60
- peerId: peer.peerId,
61
- peerName: peer.displayName,
62
- });
63
- }
64
-
65
- clearTimeout(timer);
66
- this.node.removeListener('search_response', handler);
67
- resolve();
68
- };
69
-
70
- this.node.on('search_response', handler);
71
-
72
- // 쿼리 전송
73
- this.node.sendSearchQuery(peer.peerId, queryId, Array.from(embedding), limit);
74
- });
75
- });
76
-
77
- await Promise.allSettled(responsePromises);
78
-
79
- // 3. 결과 병합 — similarity 내림차순
80
- return results
81
- .sort((a, b) => b.similarity - a.similarity)
82
- .slice(0, limit);
83
- }
84
-
85
- // Design Ref: §5 — startResponder() 피어 요청 수신 측
86
- startResponder(): void {
87
- this.node.on('search_request', async (req: {
88
- queryId: string;
89
- embedding: number[];
90
- limit: number;
91
- respondTo: string | null;
92
- }) => {
93
- if (!req.respondTo) return;
94
-
95
- try {
96
- // 받은 임베딩으로 모든 로컬 vault DB 검색 (multi-vault)
97
- const allStores = [this.store, ...this.additionalStores];
98
- const allScored = await Promise.all(
99
- allStores.map(s => s.searchSemantic(req.embedding, req.limit).catch(() => []))
100
- );
101
- const scored = allScored.flat().sort((a, b) => b.score - a.score).slice(0, req.limit);
102
-
103
- // Plan SC: SC3 — 원문 비노출. 제목+유사도+50자만.
104
- const safe: Array<{ title: string; similarity: number; snippet: string }> = [];
105
- for (const s of scored) {
106
- const chunk = await this.store.getChunk(s.chunkId);
107
- if (!chunk) continue;
108
- // 청크의 documentId에서 문서 제목 가져오기
109
- const doc = await this.store.getDocument(chunk.documentId);
110
- if (!doc) continue;
111
-
112
- // Sharing filter: 비공개 문서는 검색 결과에서 제외
113
- if (!isDocumentShareable({ tags: doc.tags, filePath: doc.filePath, id: doc.id, content: doc.content })) continue;
114
-
115
- safe.push({
116
- title: doc.title ?? chunk.heading ?? 'Untitled',
117
- similarity: Math.round(s.score * 1000) / 1000,
118
- snippet: sanitizeSnippet(maskSnippet(chunk.content.slice(0, 50), 0.2)),
119
- });
120
- }
121
-
122
- this.node.sendSearchResult(req.respondTo, req.queryId, safe);
123
- } catch (err) {
124
- // 검색 실패 시 빈 결과 반환
125
- this.node.sendSearchResult(req.respondTo, req.queryId, []);
126
- }
127
- });
128
- }
129
- }