@remnic/core 9.69.23 → 9.69.25

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 (438) hide show
  1. package/dist/abstraction-nodes.js +3 -2
  2. package/dist/access-admin-ops-surface.d.ts +1 -1
  3. package/dist/access-admin-ops-surface.js +53 -53
  4. package/dist/access-authorization-probe.d.ts +1 -1
  5. package/dist/access-authorization-probe.js +54 -54
  6. package/dist/access-boundary.d.ts +1 -1
  7. package/dist/access-boundary.js +53 -53
  8. package/dist/access-citation-namespace.js +3 -3
  9. package/dist/access-cli.js +112 -112
  10. package/dist/access-extraction-force-flush.d.ts +1 -1
  11. package/dist/access-extraction-force-flush.js +53 -53
  12. package/dist/access-http-briefing.d.ts +1 -1
  13. package/dist/access-http-briefing.js +54 -54
  14. package/dist/access-http-lcm-compaction.d.ts +1 -1
  15. package/dist/access-http-lifecycle-flush.d.ts +1 -1
  16. package/dist/access-http-offline-stream.d.ts +1 -1
  17. package/dist/access-http-query.js +55 -55
  18. package/dist/access-http.d.ts +2 -2
  19. package/dist/access-http.js +72 -72
  20. package/dist/access-identity-continuity-surface.js +53 -53
  21. package/dist/access-lcm-surface.d.ts +1 -1
  22. package/dist/access-lcm-surface.js +53 -53
  23. package/dist/access-mcp.d.ts +1 -1
  24. package/dist/access-mcp.js +64 -64
  25. package/dist/access-namespace-preflight.js +53 -53
  26. package/dist/access-observe-write-surface.d.ts +1 -1
  27. package/dist/access-observe-write-surface.js +53 -53
  28. package/dist/access-offline-manifest.js +10 -10
  29. package/dist/access-operations-batch.js +58 -58
  30. package/dist/access-operations.d.ts +1 -1
  31. package/dist/access-operations.js +63 -63
  32. package/dist/access-recall-concurrency.d.ts +1 -1
  33. package/dist/access-recall-concurrency.js +53 -53
  34. package/dist/access-recall-response.d.ts +1 -1
  35. package/dist/access-recall-response.js +53 -53
  36. package/dist/access-recall-surface.d.ts +1 -1
  37. package/dist/access-recall-surface.js +53 -53
  38. package/dist/access-schema.js +6 -5
  39. package/dist/access-service-helpers.d.ts +1 -1
  40. package/dist/access-service.d.ts +1 -1
  41. package/dist/access-service.js +53 -53
  42. package/dist/access-surface-catalog.d.ts +1 -1
  43. package/dist/access-surface-catalog.js +55 -55
  44. package/dist/active-recall.js +12 -11
  45. package/dist/active-recall.js.map +1 -1
  46. package/dist/{auto-sync-TTIEWJ5X.js → auto-sync-WNGG2GC2.js} +7 -7
  47. package/dist/briefing.js +20 -20
  48. package/dist/buffer.js +9 -9
  49. package/dist/calibration.js +2 -1
  50. package/dist/calibration.js.map +1 -1
  51. package/dist/{capsule-merge-CU6QJBSV.js → capsule-merge-IPG4IOFP.js} +4 -4
  52. package/dist/causal-behavior.js +4 -3
  53. package/dist/causal-behavior.js.map +1 -1
  54. package/dist/causal-chain.js +4 -3
  55. package/dist/causal-consolidation.js +25 -25
  56. package/dist/causal-retrieval.js +4 -3
  57. package/dist/causal-retrieval.js.map +1 -1
  58. package/dist/causal-trajectory-graph.js +2 -1
  59. package/dist/causal-trajectory-graph.js.map +1 -1
  60. package/dist/causal-trajectory.js +3 -2
  61. package/dist/{chunk-5RWHODVF.js → chunk-27QVNSQ3.js} +2 -2
  62. package/dist/{chunk-2MX7RU7B.js → chunk-2EKJDQZB.js} +2 -2
  63. package/dist/{chunk-XLRM6PPI.js → chunk-2IOHTUP3.js} +4 -4
  64. package/dist/{chunk-ZGQDTD5T.js → chunk-2ITE4C2Z.js} +2 -2
  65. package/dist/{chunk-O5ZR7SXV.js → chunk-2SGLMP2E.js} +2 -2
  66. package/dist/{chunk-FYWLSFFS.js → chunk-2Z4GS5E6.js} +2 -2
  67. package/dist/{chunk-WELP4CG6.js → chunk-37KUQPX4.js} +6 -6
  68. package/dist/{chunk-DDQQY2E3.js → chunk-3BTFBQLO.js} +7 -7
  69. package/dist/chunk-3BTFBQLO.js.map +1 -0
  70. package/dist/{chunk-UR6PBX2J.js → chunk-3K7V3HE6.js} +35 -60
  71. package/dist/chunk-3K7V3HE6.js.map +1 -0
  72. package/dist/{chunk-MRSLR6TB.js → chunk-3QQTXYZ6.js} +2 -2
  73. package/dist/{chunk-DJUKBGAD.js → chunk-46EST7JO.js} +5 -5
  74. package/dist/chunk-46EST7JO.js.map +1 -0
  75. package/dist/{chunk-CI6C33EO.js → chunk-46ZPIGWI.js} +3 -3
  76. package/dist/{chunk-HTIIXNJQ.js → chunk-4FIH6MPS.js} +6 -3
  77. package/dist/chunk-4FIH6MPS.js.map +1 -0
  78. package/dist/{chunk-MCA2X4WH.js → chunk-4IHBN6WU.js} +2 -2
  79. package/dist/{chunk-W7IGLX4G.js → chunk-4O6WRBGE.js} +7 -7
  80. package/dist/chunk-4O6WRBGE.js.map +1 -0
  81. package/dist/{chunk-TOZCM7WN.js → chunk-4TKJGOCJ.js} +2 -2
  82. package/dist/{chunk-3ADRFFRO.js → chunk-54WHLA65.js} +4 -4
  83. package/dist/{chunk-Z2N2AHEM.js → chunk-56Y6EKZN.js} +2 -2
  84. package/dist/{chunk-2H2N5UQW.js → chunk-5ATKSPEQ.js} +2 -2
  85. package/dist/{chunk-MSOXFXCA.js → chunk-5FAGCOZD.js} +5 -5
  86. package/dist/chunk-5FAGCOZD.js.map +1 -0
  87. package/dist/{chunk-ZVZHG7AI.js → chunk-5UBH37SL.js} +3 -3
  88. package/dist/{chunk-YZYZ2BEU.js → chunk-66OJSCI6.js} +2 -2
  89. package/dist/{chunk-HNPE66LB.js → chunk-6CVNSDCZ.js} +4 -4
  90. package/dist/{chunk-ERVJFFTR.js → chunk-6NXSYYGP.js} +2 -2
  91. package/dist/{chunk-2HIJHXB3.js → chunk-6WHJ2EAB.js} +2 -2
  92. package/dist/{chunk-34VTBPNE.js → chunk-6XL73HQ4.js} +4 -4
  93. package/dist/{chunk-YK3UIF7X.js → chunk-AQ7SYDVO.js} +2 -2
  94. package/dist/{chunk-DSCCM66R.js → chunk-B3O3IRZN.js} +2 -2
  95. package/dist/{chunk-P77QX3ID.js → chunk-B6O2YLUR.js} +21 -20
  96. package/dist/chunk-B6O2YLUR.js.map +1 -0
  97. package/dist/{chunk-N37X5RU7.js → chunk-BD7JTBYP.js} +2 -2
  98. package/dist/{chunk-VO43BJ2F.js → chunk-BLJWYCNO.js} +5 -5
  99. package/dist/{chunk-ACPCA4NO.js → chunk-BMWN7B3Y.js} +6 -6
  100. package/dist/chunk-BMWN7B3Y.js.map +1 -0
  101. package/dist/{chunk-HSKSVY3Q.js → chunk-C553ZTLF.js} +15 -15
  102. package/dist/{chunk-GCASGYIO.js → chunk-C7HJ3NEI.js} +2 -2
  103. package/dist/{chunk-WVGXCBOC.js → chunk-D5F7TKMH.js} +2 -2
  104. package/dist/{chunk-UFT2XNBW.js → chunk-DGS34QSY.js} +2 -2
  105. package/dist/{chunk-VAOL3SOT.js → chunk-DZD3WGCD.js} +4 -4
  106. package/dist/{chunk-KHMS2FQS.js → chunk-E2P7TZTF.js} +2 -2
  107. package/dist/{chunk-6FC3IZ26.js → chunk-EBA5DA77.js} +2 -2
  108. package/dist/{chunk-E6EANYLD.js → chunk-EOQ6FSQP.js} +2 -2
  109. package/dist/{chunk-7RPPCA26.js → chunk-FVOP3NT7.js} +2 -2
  110. package/dist/{chunk-NRLELHAY.js → chunk-G7NYVKD6.js} +2 -2
  111. package/dist/{chunk-QY34X2QJ.js → chunk-GHTSNGBZ.js} +2 -2
  112. package/dist/{chunk-SLIOMMPF.js → chunk-H272ZPQ3.js} +5 -5
  113. package/dist/{chunk-ZZBQNQS6.js → chunk-H3TKENU4.js} +2 -2
  114. package/dist/{chunk-5OPNUUBX.js → chunk-H4SEGIZY.js} +2 -2
  115. package/dist/{chunk-F2HMDGLC.js → chunk-H54VWRPS.js} +13 -13
  116. package/dist/{chunk-HTP6XRUI.js → chunk-HM7RHKS4.js} +2 -2
  117. package/dist/{chunk-O7H3P2SJ.js → chunk-HWLIMQE2.js} +2 -2
  118. package/dist/{chunk-62WZDHTW.js → chunk-ICKJ52PE.js} +33 -33
  119. package/dist/chunk-ICKJ52PE.js.map +1 -0
  120. package/dist/{chunk-I3FDDCY3.js → chunk-JEC4DVM3.js} +8 -8
  121. package/dist/chunk-JEC4DVM3.js.map +1 -0
  122. package/dist/{chunk-ET2CNMLD.js → chunk-JN72EPOE.js} +2 -2
  123. package/dist/{chunk-E7UQOS4C.js → chunk-JPKK466T.js} +2 -2
  124. package/dist/{chunk-JCCWJHOP.js → chunk-JYZSRNR7.js} +2 -2
  125. package/dist/{chunk-7IUESBLV.js → chunk-K7724CH2.js} +2 -2
  126. package/dist/{chunk-UK7HXNNJ.js → chunk-KAXCYM66.js} +3 -3
  127. package/dist/{chunk-7XVP4P4O.js → chunk-KB2G2I6Q.js} +3 -3
  128. package/dist/{chunk-K7LTRJZU.js → chunk-KEF46KL2.js} +2 -2
  129. package/dist/{chunk-5UZXUTVO.js → chunk-KNA3BXXL.js} +6 -2
  130. package/dist/chunk-KNA3BXXL.js.map +1 -0
  131. package/dist/{chunk-JYYTWCPU.js → chunk-KTWG7CNY.js} +6 -6
  132. package/dist/{chunk-XTYDEO7M.js → chunk-L7Z57SID.js} +2 -2
  133. package/dist/{chunk-EYMPUXAN.js → chunk-LO4UKPKX.js} +3 -3
  134. package/dist/{chunk-LDWIPYJ6.js → chunk-LS2FHUML.js} +3 -3
  135. package/dist/{chunk-GDB4J2H3.js → chunk-MPC7TYTZ.js} +2 -2
  136. package/dist/{chunk-2GF27PGH.js → chunk-MRPOZBJC.js} +3 -3
  137. package/dist/{chunk-7OLKAQMG.js → chunk-MWN6QEI2.js} +2 -2
  138. package/dist/{chunk-J62HG52Z.js → chunk-MY5EDR46.js} +4 -4
  139. package/dist/{chunk-IZRMWPGS.js → chunk-N3ZOP7KC.js} +2 -2
  140. package/dist/{chunk-N6A2RP5S.js → chunk-NB3LRY4T.js} +3 -3
  141. package/dist/{chunk-4N5BIR2U.js → chunk-ND6IQGSZ.js} +2 -2
  142. package/dist/{chunk-NOB2T2FC.js → chunk-NHLLKEKK.js} +2 -2
  143. package/dist/{chunk-WW6B7NQJ.js → chunk-NLYVH66G.js} +6 -6
  144. package/dist/chunk-NLYVH66G.js.map +1 -0
  145. package/dist/{chunk-M5CQNOQN.js → chunk-O6ZNNVSP.js} +2 -2
  146. package/dist/{chunk-NNBZS3DY.js → chunk-OB3XMWX5.js} +2 -2
  147. package/dist/{chunk-TXJNRGMI.js → chunk-OEYZXDQI.js} +6 -6
  148. package/dist/chunk-OEYZXDQI.js.map +1 -0
  149. package/dist/{chunk-SIBVIP2Y.js → chunk-PAZY2ZKP.js} +2 -2
  150. package/dist/{chunk-LXESHEBP.js → chunk-PX4UMA5Z.js} +2 -2
  151. package/dist/{chunk-4KNRKJXQ.js → chunk-QOOBICJF.js} +5 -5
  152. package/dist/chunk-QOOBICJF.js.map +1 -0
  153. package/dist/{chunk-NNZFPYYX.js → chunk-R7QY5ZVB.js} +2 -2
  154. package/dist/{chunk-WTRTFIIN.js → chunk-R7RTXEYG.js} +2 -2
  155. package/dist/{chunk-XRBJ5R3P.js → chunk-RBCQVOVJ.js} +3 -3
  156. package/dist/{chunk-WFZNT4KB.js → chunk-RC5DXXWC.js} +2 -2
  157. package/dist/{chunk-OH7LZHGJ.js → chunk-RJYJ7KR7.js} +52 -52
  158. package/dist/{chunk-OH7LZHGJ.js.map → chunk-RJYJ7KR7.js.map} +1 -1
  159. package/dist/{chunk-5QZR2RA3.js → chunk-ROBHL3GL.js} +2 -2
  160. package/dist/{chunk-6PST2SFW.js → chunk-SCXURCVT.js} +3 -3
  161. package/dist/{chunk-AYG7ML7O.js → chunk-SJDQ5RSN.js} +3 -3
  162. package/dist/{chunk-3ZBLKIHJ.js → chunk-SMWTZLHE.js} +51 -41
  163. package/dist/{chunk-3ZBLKIHJ.js.map → chunk-SMWTZLHE.js.map} +1 -1
  164. package/dist/{chunk-IQXDSKTL.js → chunk-SVXJLDDC.js} +6 -6
  165. package/dist/{chunk-SEF4IOFE.js → chunk-SWIKABKI.js} +2 -2
  166. package/dist/{chunk-ZJABRLCZ.js → chunk-TBXAY2SS.js} +4 -4
  167. package/dist/{chunk-GIC6BASP.js → chunk-TNSCIPBQ.js} +2 -2
  168. package/dist/{chunk-ZMDMHSV2.js → chunk-TVEONGBU.js} +2 -2
  169. package/dist/{chunk-4FSEZRGK.js → chunk-TWF35IC6.js} +2 -2
  170. package/dist/{chunk-LS2SGMQE.js → chunk-U6N5IBVY.js} +2 -2
  171. package/dist/{chunk-62YW6OYI.js → chunk-UCKYTA2T.js} +3 -3
  172. package/dist/{chunk-YFCHNOGJ.js → chunk-UNNPNBR2.js} +9 -9
  173. package/dist/{chunk-Z2M7F4QM.js → chunk-VVX5PZFS.js} +3 -3
  174. package/dist/{chunk-NTYLZXDX.js → chunk-VYCOJKSX.js} +2 -2
  175. package/dist/{chunk-UICSQESY.js → chunk-W24T5YMW.js} +2 -2
  176. package/dist/{chunk-HDQUQBPW.js → chunk-W3K3HITK.js} +2 -2
  177. package/dist/{chunk-GDASG7NC.js → chunk-W4F3C7N7.js} +2 -2
  178. package/dist/{chunk-YBLZFNIQ.js → chunk-WJHGDE7X.js} +2 -2
  179. package/dist/{chunk-ZBPXG5PJ.js → chunk-WMLEPWMO.js} +9 -9
  180. package/dist/chunk-WMLEPWMO.js.map +1 -0
  181. package/dist/{chunk-4F24PHNX.js → chunk-WQZZDN5M.js} +2 -2
  182. package/dist/{chunk-CDZEUCV7.js → chunk-X5K5TAQZ.js} +4 -4
  183. package/dist/{chunk-5AUODSOQ.js → chunk-XM24CDZX.js} +3 -3
  184. package/dist/{chunk-6VML2LII.js → chunk-XOVKXJEP.js} +3 -3
  185. package/dist/{chunk-OU5TIWDQ.js → chunk-XSGUMQQQ.js} +12 -12
  186. package/dist/{chunk-7CFVBWDC.js → chunk-XUE46UYW.js} +3 -3
  187. package/dist/{chunk-DJORULH3.js → chunk-YRLHEEQT.js} +2 -2
  188. package/dist/{chunk-YRWDPE32.js → chunk-Z3O53WZR.js} +2 -2
  189. package/dist/{chunk-CSY5DA7O.js → chunk-Z6COGHHN.js} +2 -2
  190. package/dist/{chunk-OYR3IPHD.js → chunk-ZIW5JVRM.js} +2 -2
  191. package/dist/{cli-B_YwqoIr.d.ts → cli-BqMNkQn5.d.ts} +1 -1
  192. package/dist/cli.d.ts +2 -2
  193. package/dist/cli.js +94 -94
  194. package/dist/coding/export-okf-codegraph.js +21 -21
  195. package/dist/coding/pre-action-gate.js +4 -3
  196. package/dist/commitment-ledger.js +3 -2
  197. package/dist/compounding/engine.js +21 -21
  198. package/dist/config.js +12 -11
  199. package/dist/connectors/codex-materialize-runner.js +21 -21
  200. package/dist/connectors/codex-materialize.js +3 -3
  201. package/dist/connectors/index.js +21 -21
  202. package/dist/consolidation-provenance-check.js +4 -4
  203. package/dist/consolidation-undo.js +3 -3
  204. package/dist/contradiction/index.js +7 -7
  205. package/dist/convergence-refresh.js +22 -22
  206. package/dist/corpus-watermark.js +22 -22
  207. package/dist/cue-anchors.js +4 -3
  208. package/dist/deep-recall-http-glue.d.ts +1 -1
  209. package/dist/deep-recall-http-glue.js +7 -6
  210. package/dist/deep-recall-mcp-tools.d.ts +1 -1
  211. package/dist/entity-retrieval.js +20 -20
  212. package/dist/eval-trajectory-store.js +4 -3
  213. package/dist/eval-trajectory.js +4 -3
  214. package/dist/evals.js +3 -2
  215. package/dist/explicit-capture.js +8 -8
  216. package/dist/external-wiki-access.d.ts +1 -1
  217. package/dist/external-wiki-access.js +54 -54
  218. package/dist/external-wiki-mcp-tools.d.ts +1 -1
  219. package/dist/extraction.js +25 -25
  220. package/dist/{first-start-migration-KHIMCBIC.js → first-start-migration-RC345GPL.js} +6 -5
  221. package/dist/{first-start-migration-KHIMCBIC.js.map → first-start-migration-RC345GPL.js.map} +1 -1
  222. package/dist/{graph-edge-decay-CJW4OT2X.js → graph-edge-decay-MKIRZ762.js} +5 -4
  223. package/dist/graph-jsonl.js +3 -2
  224. package/dist/graph-snapshot.js +3 -2
  225. package/dist/graph.js +2 -1
  226. package/dist/harmonic-construction.js +5 -4
  227. package/dist/harmonic-retrieval.js +5 -4
  228. package/dist/index.d.ts +19 -7
  229. package/dist/index.js +114 -112
  230. package/dist/json-store.js +2 -1
  231. package/dist/live-connectors-runner.js +3 -2
  232. package/dist/location/index.js +23 -23
  233. package/dist/maintenance/memory-governance.js +20 -20
  234. package/dist/maintenance/rebuild-memory-lifecycle-ledger.js +20 -20
  235. package/dist/maintenance/rebuild-memory-projection.js +21 -21
  236. package/dist/mcp-memory-inspector-app.d.ts +1 -1
  237. package/dist/memory-projection-mutations.js +3 -3
  238. package/dist/memory-subject-cli.d.ts +1 -1
  239. package/dist/memory-subject.d.ts +1 -1
  240. package/dist/memory-subject.js +4 -4
  241. package/dist/namespaces/migrate.js +21 -21
  242. package/dist/namespaces/search.js +8 -8
  243. package/dist/namespaces/storage.js +20 -20
  244. package/dist/objective-state-writers.js +4 -3
  245. package/dist/objective-state.js +3 -2
  246. package/dist/offline-sync-file-io.js +4 -3
  247. package/dist/offline-sync-impression-drain.js +5 -5
  248. package/dist/offline-sync.js +5 -4
  249. package/dist/operator-doctor-corpus.js +23 -23
  250. package/dist/operator-toolkit.js +38 -38
  251. package/dist/orchestration/maintenance.js +29 -29
  252. package/dist/orchestrator.js +112 -112
  253. package/dist/page-versioning.js +3 -3
  254. package/dist/{public-http-D6d4W8x-.d.ts → public-http-ByX2eTla.d.ts} +1 -1
  255. package/dist/{purge-OP6BEDFY.js → purge-TZKRE6ZQ.js} +5 -5
  256. package/dist/purge-TZKRE6ZQ.js.map +1 -0
  257. package/dist/recall-state.js +3 -3
  258. package/dist/reconcile/manifest.js +4 -4
  259. package/dist/{resolution-U5O4QANY.js → resolution-VKATP2HT.js} +8 -8
  260. package/dist/resume-bundles.js +16 -15
  261. package/dist/salvage-envelope.js +6 -6
  262. package/dist/schemas.d.ts +42 -42
  263. package/dist/search/document-scanner.js +3 -3
  264. package/dist/search/factory.js +7 -7
  265. package/dist/search/index.js +7 -7
  266. package/dist/search/lancedb-backend.js +4 -4
  267. package/dist/search/meilisearch-backend.js +4 -4
  268. package/dist/search/orama-backend.js +4 -4
  269. package/dist/secure-store/index.js +3 -3
  270. package/dist/semantic-consolidation.js +22 -22
  271. package/dist/semantic-rule-promotion.js +20 -20
  272. package/dist/semantic-rule-verifier.js +20 -20
  273. package/dist/source-agent-qualifier.js +24 -24
  274. package/dist/standup/build.js +20 -20
  275. package/dist/storage.js +19 -19
  276. package/dist/subject-config.js +5 -5
  277. package/dist/support-passport/index.d.ts +4 -4
  278. package/dist/support-passport/index.js +56 -56
  279. package/dist/{tier-stats-2TOW3QNL.js → tier-stats-KA6OZX2C.js} +6 -5
  280. package/dist/{tier-stats-2TOW3QNL.js.map → tier-stats-KA6OZX2C.js.map} +1 -1
  281. package/dist/transfer/capsule-import.js +4 -4
  282. package/dist/transfer/export-okf.js +21 -21
  283. package/dist/transfer/types.d.ts +12 -12
  284. package/dist/trust-zones.js +3 -2
  285. package/dist/utility-learner.js +4 -3
  286. package/dist/utility-runtime.js +5 -4
  287. package/dist/utility-telemetry.js +3 -2
  288. package/dist/verified-recall.js +20 -20
  289. package/dist/who-knows-cli.d.ts +1 -1
  290. package/dist/who-knows-cli.js +21 -21
  291. package/dist/who-knows.d.ts +1 -1
  292. package/dist/who-knows.js +20 -20
  293. package/dist/work/board.js +3 -3
  294. package/dist/work/storage.js +2 -2
  295. package/dist/work-product-ledger.js +3 -2
  296. package/dist/write-envelope.js +5 -5
  297. package/package.json +2 -2
  298. package/src/abstraction-nodes.ts +1 -4
  299. package/src/binary-lifecycle/backend.ts +2 -1
  300. package/src/connectors/live/github.ts +10 -17
  301. package/src/connectors/live/gmail.ts +8 -19
  302. package/src/connectors/live/google-drive.ts +6 -13
  303. package/src/connectors/live/notion.ts +11 -21
  304. package/src/cue-anchors.ts +1 -6
  305. package/src/graph.ts +2 -4
  306. package/src/json-store.ts +17 -20
  307. package/src/live-connectors-runner.ts +2 -1
  308. package/src/location/store.ts +1 -4
  309. package/src/maintenance/purge.ts +2 -5
  310. package/src/maintenance/rebuild-memory-lifecycle-ledger.ts +3 -6
  311. package/src/maintenance/rebuild-memory-projection.ts +2 -5
  312. package/src/namespaces/catalog.ts +1 -9
  313. package/src/offline-sync-file-io.test.ts +39 -0
  314. package/src/offline-sync-file-io.ts +3 -7
  315. package/src/procedural/procedure-miner.ts +1 -9
  316. package/src/search/document-scanner.ts +3 -6
  317. package/src/semantic-rule-promotion.ts +1 -4
  318. package/src/utils/errno.test.ts +31 -0
  319. package/src/utils/errno.ts +5 -0
  320. package/src/wearables/index.ts +1 -0
  321. package/src/wearables/registry.ts +23 -0
  322. package/dist/chunk-4KNRKJXQ.js.map +0 -1
  323. package/dist/chunk-5UZXUTVO.js.map +0 -1
  324. package/dist/chunk-62WZDHTW.js.map +0 -1
  325. package/dist/chunk-ACPCA4NO.js.map +0 -1
  326. package/dist/chunk-DDQQY2E3.js.map +0 -1
  327. package/dist/chunk-DJUKBGAD.js.map +0 -1
  328. package/dist/chunk-HTIIXNJQ.js.map +0 -1
  329. package/dist/chunk-I3FDDCY3.js.map +0 -1
  330. package/dist/chunk-MSOXFXCA.js.map +0 -1
  331. package/dist/chunk-P77QX3ID.js.map +0 -1
  332. package/dist/chunk-TXJNRGMI.js.map +0 -1
  333. package/dist/chunk-UR6PBX2J.js.map +0 -1
  334. package/dist/chunk-W7IGLX4G.js.map +0 -1
  335. package/dist/chunk-WW6B7NQJ.js.map +0 -1
  336. package/dist/chunk-ZBPXG5PJ.js.map +0 -1
  337. package/dist/purge-OP6BEDFY.js.map +0 -1
  338. package/dist/{access-service-Cv8Rizo0.d.ts → access-service-GrdVg_-Z.d.ts} +6 -6
  339. /package/dist/{auto-sync-TTIEWJ5X.js.map → auto-sync-WNGG2GC2.js.map} +0 -0
  340. /package/dist/{capsule-merge-CU6QJBSV.js.map → capsule-merge-IPG4IOFP.js.map} +0 -0
  341. /package/dist/{chunk-5RWHODVF.js.map → chunk-27QVNSQ3.js.map} +0 -0
  342. /package/dist/{chunk-2MX7RU7B.js.map → chunk-2EKJDQZB.js.map} +0 -0
  343. /package/dist/{chunk-XLRM6PPI.js.map → chunk-2IOHTUP3.js.map} +0 -0
  344. /package/dist/{chunk-ZGQDTD5T.js.map → chunk-2ITE4C2Z.js.map} +0 -0
  345. /package/dist/{chunk-O5ZR7SXV.js.map → chunk-2SGLMP2E.js.map} +0 -0
  346. /package/dist/{chunk-FYWLSFFS.js.map → chunk-2Z4GS5E6.js.map} +0 -0
  347. /package/dist/{chunk-WELP4CG6.js.map → chunk-37KUQPX4.js.map} +0 -0
  348. /package/dist/{chunk-MRSLR6TB.js.map → chunk-3QQTXYZ6.js.map} +0 -0
  349. /package/dist/{chunk-CI6C33EO.js.map → chunk-46ZPIGWI.js.map} +0 -0
  350. /package/dist/{chunk-MCA2X4WH.js.map → chunk-4IHBN6WU.js.map} +0 -0
  351. /package/dist/{chunk-TOZCM7WN.js.map → chunk-4TKJGOCJ.js.map} +0 -0
  352. /package/dist/{chunk-3ADRFFRO.js.map → chunk-54WHLA65.js.map} +0 -0
  353. /package/dist/{chunk-Z2N2AHEM.js.map → chunk-56Y6EKZN.js.map} +0 -0
  354. /package/dist/{chunk-2H2N5UQW.js.map → chunk-5ATKSPEQ.js.map} +0 -0
  355. /package/dist/{chunk-ZVZHG7AI.js.map → chunk-5UBH37SL.js.map} +0 -0
  356. /package/dist/{chunk-YZYZ2BEU.js.map → chunk-66OJSCI6.js.map} +0 -0
  357. /package/dist/{chunk-HNPE66LB.js.map → chunk-6CVNSDCZ.js.map} +0 -0
  358. /package/dist/{chunk-ERVJFFTR.js.map → chunk-6NXSYYGP.js.map} +0 -0
  359. /package/dist/{chunk-2HIJHXB3.js.map → chunk-6WHJ2EAB.js.map} +0 -0
  360. /package/dist/{chunk-34VTBPNE.js.map → chunk-6XL73HQ4.js.map} +0 -0
  361. /package/dist/{chunk-YK3UIF7X.js.map → chunk-AQ7SYDVO.js.map} +0 -0
  362. /package/dist/{chunk-DSCCM66R.js.map → chunk-B3O3IRZN.js.map} +0 -0
  363. /package/dist/{chunk-N37X5RU7.js.map → chunk-BD7JTBYP.js.map} +0 -0
  364. /package/dist/{chunk-VO43BJ2F.js.map → chunk-BLJWYCNO.js.map} +0 -0
  365. /package/dist/{chunk-HSKSVY3Q.js.map → chunk-C553ZTLF.js.map} +0 -0
  366. /package/dist/{chunk-GCASGYIO.js.map → chunk-C7HJ3NEI.js.map} +0 -0
  367. /package/dist/{chunk-WVGXCBOC.js.map → chunk-D5F7TKMH.js.map} +0 -0
  368. /package/dist/{chunk-UFT2XNBW.js.map → chunk-DGS34QSY.js.map} +0 -0
  369. /package/dist/{chunk-VAOL3SOT.js.map → chunk-DZD3WGCD.js.map} +0 -0
  370. /package/dist/{chunk-KHMS2FQS.js.map → chunk-E2P7TZTF.js.map} +0 -0
  371. /package/dist/{chunk-6FC3IZ26.js.map → chunk-EBA5DA77.js.map} +0 -0
  372. /package/dist/{chunk-E6EANYLD.js.map → chunk-EOQ6FSQP.js.map} +0 -0
  373. /package/dist/{chunk-7RPPCA26.js.map → chunk-FVOP3NT7.js.map} +0 -0
  374. /package/dist/{chunk-NRLELHAY.js.map → chunk-G7NYVKD6.js.map} +0 -0
  375. /package/dist/{chunk-QY34X2QJ.js.map → chunk-GHTSNGBZ.js.map} +0 -0
  376. /package/dist/{chunk-SLIOMMPF.js.map → chunk-H272ZPQ3.js.map} +0 -0
  377. /package/dist/{chunk-ZZBQNQS6.js.map → chunk-H3TKENU4.js.map} +0 -0
  378. /package/dist/{chunk-5OPNUUBX.js.map → chunk-H4SEGIZY.js.map} +0 -0
  379. /package/dist/{chunk-F2HMDGLC.js.map → chunk-H54VWRPS.js.map} +0 -0
  380. /package/dist/{chunk-HTP6XRUI.js.map → chunk-HM7RHKS4.js.map} +0 -0
  381. /package/dist/{chunk-O7H3P2SJ.js.map → chunk-HWLIMQE2.js.map} +0 -0
  382. /package/dist/{chunk-ET2CNMLD.js.map → chunk-JN72EPOE.js.map} +0 -0
  383. /package/dist/{chunk-E7UQOS4C.js.map → chunk-JPKK466T.js.map} +0 -0
  384. /package/dist/{chunk-JCCWJHOP.js.map → chunk-JYZSRNR7.js.map} +0 -0
  385. /package/dist/{chunk-7IUESBLV.js.map → chunk-K7724CH2.js.map} +0 -0
  386. /package/dist/{chunk-UK7HXNNJ.js.map → chunk-KAXCYM66.js.map} +0 -0
  387. /package/dist/{chunk-7XVP4P4O.js.map → chunk-KB2G2I6Q.js.map} +0 -0
  388. /package/dist/{chunk-K7LTRJZU.js.map → chunk-KEF46KL2.js.map} +0 -0
  389. /package/dist/{chunk-JYYTWCPU.js.map → chunk-KTWG7CNY.js.map} +0 -0
  390. /package/dist/{chunk-XTYDEO7M.js.map → chunk-L7Z57SID.js.map} +0 -0
  391. /package/dist/{chunk-EYMPUXAN.js.map → chunk-LO4UKPKX.js.map} +0 -0
  392. /package/dist/{chunk-LDWIPYJ6.js.map → chunk-LS2FHUML.js.map} +0 -0
  393. /package/dist/{chunk-GDB4J2H3.js.map → chunk-MPC7TYTZ.js.map} +0 -0
  394. /package/dist/{chunk-2GF27PGH.js.map → chunk-MRPOZBJC.js.map} +0 -0
  395. /package/dist/{chunk-7OLKAQMG.js.map → chunk-MWN6QEI2.js.map} +0 -0
  396. /package/dist/{chunk-J62HG52Z.js.map → chunk-MY5EDR46.js.map} +0 -0
  397. /package/dist/{chunk-IZRMWPGS.js.map → chunk-N3ZOP7KC.js.map} +0 -0
  398. /package/dist/{chunk-N6A2RP5S.js.map → chunk-NB3LRY4T.js.map} +0 -0
  399. /package/dist/{chunk-4N5BIR2U.js.map → chunk-ND6IQGSZ.js.map} +0 -0
  400. /package/dist/{chunk-NOB2T2FC.js.map → chunk-NHLLKEKK.js.map} +0 -0
  401. /package/dist/{chunk-M5CQNOQN.js.map → chunk-O6ZNNVSP.js.map} +0 -0
  402. /package/dist/{chunk-NNBZS3DY.js.map → chunk-OB3XMWX5.js.map} +0 -0
  403. /package/dist/{chunk-SIBVIP2Y.js.map → chunk-PAZY2ZKP.js.map} +0 -0
  404. /package/dist/{chunk-LXESHEBP.js.map → chunk-PX4UMA5Z.js.map} +0 -0
  405. /package/dist/{chunk-NNZFPYYX.js.map → chunk-R7QY5ZVB.js.map} +0 -0
  406. /package/dist/{chunk-WTRTFIIN.js.map → chunk-R7RTXEYG.js.map} +0 -0
  407. /package/dist/{chunk-XRBJ5R3P.js.map → chunk-RBCQVOVJ.js.map} +0 -0
  408. /package/dist/{chunk-WFZNT4KB.js.map → chunk-RC5DXXWC.js.map} +0 -0
  409. /package/dist/{chunk-5QZR2RA3.js.map → chunk-ROBHL3GL.js.map} +0 -0
  410. /package/dist/{chunk-6PST2SFW.js.map → chunk-SCXURCVT.js.map} +0 -0
  411. /package/dist/{chunk-AYG7ML7O.js.map → chunk-SJDQ5RSN.js.map} +0 -0
  412. /package/dist/{chunk-IQXDSKTL.js.map → chunk-SVXJLDDC.js.map} +0 -0
  413. /package/dist/{chunk-SEF4IOFE.js.map → chunk-SWIKABKI.js.map} +0 -0
  414. /package/dist/{chunk-ZJABRLCZ.js.map → chunk-TBXAY2SS.js.map} +0 -0
  415. /package/dist/{chunk-GIC6BASP.js.map → chunk-TNSCIPBQ.js.map} +0 -0
  416. /package/dist/{chunk-ZMDMHSV2.js.map → chunk-TVEONGBU.js.map} +0 -0
  417. /package/dist/{chunk-4FSEZRGK.js.map → chunk-TWF35IC6.js.map} +0 -0
  418. /package/dist/{chunk-LS2SGMQE.js.map → chunk-U6N5IBVY.js.map} +0 -0
  419. /package/dist/{chunk-62YW6OYI.js.map → chunk-UCKYTA2T.js.map} +0 -0
  420. /package/dist/{chunk-YFCHNOGJ.js.map → chunk-UNNPNBR2.js.map} +0 -0
  421. /package/dist/{chunk-Z2M7F4QM.js.map → chunk-VVX5PZFS.js.map} +0 -0
  422. /package/dist/{chunk-NTYLZXDX.js.map → chunk-VYCOJKSX.js.map} +0 -0
  423. /package/dist/{chunk-UICSQESY.js.map → chunk-W24T5YMW.js.map} +0 -0
  424. /package/dist/{chunk-HDQUQBPW.js.map → chunk-W3K3HITK.js.map} +0 -0
  425. /package/dist/{chunk-GDASG7NC.js.map → chunk-W4F3C7N7.js.map} +0 -0
  426. /package/dist/{chunk-YBLZFNIQ.js.map → chunk-WJHGDE7X.js.map} +0 -0
  427. /package/dist/{chunk-4F24PHNX.js.map → chunk-WQZZDN5M.js.map} +0 -0
  428. /package/dist/{chunk-CDZEUCV7.js.map → chunk-X5K5TAQZ.js.map} +0 -0
  429. /package/dist/{chunk-5AUODSOQ.js.map → chunk-XM24CDZX.js.map} +0 -0
  430. /package/dist/{chunk-6VML2LII.js.map → chunk-XOVKXJEP.js.map} +0 -0
  431. /package/dist/{chunk-OU5TIWDQ.js.map → chunk-XSGUMQQQ.js.map} +0 -0
  432. /package/dist/{chunk-7CFVBWDC.js.map → chunk-XUE46UYW.js.map} +0 -0
  433. /package/dist/{chunk-DJORULH3.js.map → chunk-YRLHEEQT.js.map} +0 -0
  434. /package/dist/{chunk-YRWDPE32.js.map → chunk-Z3O53WZR.js.map} +0 -0
  435. /package/dist/{chunk-CSY5DA7O.js.map → chunk-Z6COGHHN.js.map} +0 -0
  436. /package/dist/{chunk-OYR3IPHD.js.map → chunk-ZIW5JVRM.js.map} +0 -0
  437. /package/dist/{graph-edge-decay-CJW4OT2X.js.map → graph-edge-decay-MKIRZ762.js.map} +0 -0
  438. /package/dist/{resolution-U5O4QANY.js.map → resolution-VKATP2HT.js.map} +0 -0
@@ -18,6 +18,7 @@ import {
18
18
  } from "../memory-lifecycle-ledger-utils.js";
19
19
  import { withHeldFileLock, type HeldFileLockOptions, type HeldFileLockController } from "../utils/serialize-mutations.js";
20
20
  import { probeEncryptedRegularFileHeader } from "../secure-store/secure-fs.js";
21
+ import { isErrnoCode } from "../utils/errno.js";
21
22
 
22
23
 
23
24
  export interface RebuildMemoryLifecycleLedgerOptions {
@@ -115,10 +116,6 @@ export interface RebuildMemoryLifecycleLedgerResult {
115
116
  rewritten?: boolean;
116
117
  }
117
118
 
118
- function isNodeError(err: unknown): err is NodeJS.ErrnoException {
119
- return typeof err === "object" && err !== null && "code" in err;
120
- }
121
-
122
119
  /** Serialized on-disk size (bytes, incl. trailing newline) of one ledger row. */
123
120
  function lifecycleRowBytes(event: MemoryLifecycleEvent): number {
124
121
  return Buffer.byteLength(`${JSON.stringify(event)}\n`, "utf8");
@@ -174,7 +171,7 @@ export async function backupExistingLedger(
174
171
  try {
175
172
  await stat(outputPath);
176
173
  } catch (err) {
177
- if (isNodeError(err) && err.code === "ENOENT") {
174
+ if (isErrnoCode(err, "ENOENT")) {
178
175
  return undefined;
179
176
  }
180
177
  throw err;
@@ -397,7 +394,7 @@ export async function rebuildMemoryLifecycleLedger(
397
394
  currentEncrypted = await probeEncryptedRegularFileHeader(outputPath);
398
395
  priorRawBuffer = await storage.readMemoryLifecycleLedgerRawBufferForCompaction();
399
396
  } catch (err) {
400
- if (!isNodeError(err) || err.code !== "ENOENT") throw err;
397
+ if (!isErrnoCode(err, "ENOENT")) throw err;
401
398
  }
402
399
  // Preserve encryption at rest (#2033). An already-encrypted ledger (or its
403
400
  // encrypted backup) MUST be rewritten encrypted even when the
@@ -76,6 +76,7 @@ import type {
76
76
  SkippedDuplicateMemory,
77
77
  SkippedDuplicateTimelineEvent,
78
78
  } from "./projection-support.js";
79
+ import { isErrnoCode } from "../utils/errno.js";
79
80
 
80
81
 
81
82
  export interface RebuildMemoryProjectionResult {
@@ -150,10 +151,6 @@ export interface RepairMemoryProjectionResult {
150
151
  rebuild?: RebuildMemoryProjectionResult;
151
152
  }
152
153
 
153
- function isNodeError(err: unknown): err is NodeJS.ErrnoException {
154
- return typeof err === "object" && err !== null && "code" in err;
155
- }
156
-
157
154
  export async function backupExistingProjection(
158
155
  memoryDir: string,
159
156
  outputPath: string,
@@ -162,7 +159,7 @@ export async function backupExistingProjection(
162
159
  try {
163
160
  await stat(outputPath);
164
161
  } catch (err) {
165
- if (isNodeError(err) && err.code === "ENOENT") {
162
+ if (isErrnoCode(err, "ENOENT")) {
166
163
  return undefined;
167
164
  }
168
165
  throw err;
@@ -22,6 +22,7 @@ import { isSafeRouteNamespace } from "../routing/engine.js";
22
22
  import { namespaceIdentityFromToken, namespaceIdentityLegacyToken, namespaceIdentityToken, normalizeNamespaceIdentity } from "./identity.js";
23
23
  import { resolveDefaultNamespaceRoot, resolveNamespaceStorageRoot } from "./storage.js";
24
24
  import { ALL_CATEGORY_DIRS } from "../utils/category-dir.js";
25
+ import { isNotFoundError } from "../utils/errno.js";
25
26
 
26
27
  /**
27
28
  * Rebuildable namespace catalog (issue #1499).
@@ -191,15 +192,6 @@ type MemoryDataRootStatus = {
191
192
  invalidMarker?: string;
192
193
  };
193
194
 
194
- function isNotFoundError(err: unknown): boolean {
195
- return (
196
- typeof err === "object" &&
197
- err !== null &&
198
- "code" in err &&
199
- (err as { code?: string }).code === "ENOENT"
200
- );
201
- }
202
-
203
195
  /**
204
196
  * Inspect `child` under `rootDir` as a memory-data marker (NIw0F / PR #1506).
205
197
  * Existence alone is not enough: a bogus marker — e.g. `facts` as a symlink or a
@@ -0,0 +1,39 @@
1
+ import assert from "node:assert/strict";
2
+ import { mkdtemp, writeFile } from "node:fs/promises";
3
+ import os from "node:os";
4
+ import path from "node:path";
5
+ import test from "node:test";
6
+
7
+ import { sha256OfflineSyncFile } from "./offline-sync-file-io.js";
8
+
9
+ async function tempFile(name: string, content: string): Promise<string> {
10
+ const dir = await mkdtemp(path.join(os.tmpdir(), `${name}-`));
11
+ const filePath = path.join(dir, `${name}.txt`);
12
+ await writeFile(filePath, content);
13
+ return filePath;
14
+ }
15
+
16
+ /** The abort guards must surface `name === "AbortError"`, not a plain Error (issue #2795). */
17
+ async function assertRejectsWithAbortError(promise: Promise<unknown>): Promise<void> {
18
+ await assert.rejects(promise, (err: unknown) => {
19
+ assert.ok(err instanceof Error, "abort must surface an Error");
20
+ assert.equal(err.name, "AbortError", "abort must preserve the AbortError name");
21
+ return true;
22
+ });
23
+ }
24
+
25
+ test("sha256OfflineSyncFile rejects with AbortError name via the per-chunk guard", async () => {
26
+ const filePath = await tempFile("offline-sync-abort", "chunk-of-bytes");
27
+ const controller = new AbortController();
28
+ controller.abort();
29
+ // A non-empty file yields at least one chunk, so the in-loop guard fires first.
30
+ await assertRejectsWithAbortError(sha256OfflineSyncFile(filePath, controller.signal));
31
+ });
32
+
33
+ test("sha256OfflineSyncFile rejects with AbortError name via the post-loop guard", async () => {
34
+ const filePath = await tempFile("offline-sync-abort-empty", "");
35
+ const controller = new AbortController();
36
+ controller.abort();
37
+ // An empty file yields no chunks, so only the trailing guard runs.
38
+ await assertRejectsWithAbortError(sha256OfflineSyncFile(filePath, controller.signal));
39
+ });
@@ -1,6 +1,7 @@
1
1
  import { createHash } from "node:crypto";
2
2
  import { createReadStream } from "node:fs";
3
3
  import { open } from "node:fs/promises";
4
+ import { throwIfAborted } from "./abort-error.js";
4
5
  import { MAGIC_HEADER_SIZE, isEncryptedFile } from "./secure-store/secure-fs.js";
5
6
 
6
7
  export interface OfflineSyncFileTarget {
@@ -10,11 +11,6 @@ export interface OfflineSyncFileTarget {
10
11
  }
11
12
 
12
13
  export type OfflineSyncExcludeFile = (target: OfflineSyncFileTarget) => boolean | Promise<boolean>;
13
-
14
- function throwIfAborted(signal: AbortSignal | undefined): void {
15
- if (signal?.aborted) throw new Error("offline sync request aborted");
16
- }
17
-
18
14
  export async function shouldExcludeOfflineSyncFile(
19
15
  excludeFile: OfflineSyncExcludeFile | undefined,
20
16
  target: OfflineSyncFileTarget
@@ -29,12 +25,12 @@ export async function sha256OfflineSyncFile(
29
25
  const hash = createHash("sha256");
30
26
  let bytes = 0;
31
27
  for await (const chunk of createReadStream(filePath)) {
32
- throwIfAborted(signal);
28
+ throwIfAborted(signal, "offline sync request aborted");
33
29
  const buffer = Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk);
34
30
  hash.update(buffer);
35
31
  bytes += buffer.length;
36
32
  }
37
- throwIfAborted(signal);
33
+ throwIfAborted(signal, "offline sync request aborted");
38
34
  return { sha256: hash.digest("hex"), bytes };
39
35
  }
40
36
 
@@ -16,6 +16,7 @@ import { buildProcedurePersistBody, normalizeProcedureSteps, type ProcedureStep
16
16
  import { clusterByKey } from "./reinforcement-core.js";
17
17
  import { log } from "../logger.js";
18
18
  import { composeMemoryEnvelope, STRUCTURED_ATTRIBUTE_LIMITS } from "../write-envelope.js";
19
+ import { isErrnoCode } from "../utils/errno.js";
19
20
 
20
21
  /** Must match truncation on `procedure_cluster` structured attribute (dedupe + storage). */
21
22
  const PROCEDURE_CLUSTER_ATTR_MAX = 500;
@@ -53,15 +54,6 @@ function clusterKeyHash(cluster: string): string {
53
54
  return createHash("sha256").update(cluster).digest("hex");
54
55
  }
55
56
 
56
- function isErrnoCode(error: unknown, code: string): boolean {
57
- return (
58
- typeof error === "object" &&
59
- error !== null &&
60
- "code" in error &&
61
- (error as { code?: unknown }).code === code
62
- );
63
- }
64
-
65
57
  function sleep(ms: number): Promise<void> {
66
58
  return new Promise((resolve) => setTimeout(resolve, ms));
67
59
  }
@@ -2,6 +2,7 @@ import path from "node:path";
2
2
  import { lstat, readdir, readFile, realpath } from "node:fs/promises";
3
3
  import { RECALL_FALLBACK_DIRS } from "../utils/category-dir.js";
4
4
  import { assertPathInsideRoot } from "../utils/path-containment.js";
5
+ import { isErrnoCode } from "../utils/errno.js";
5
6
 
6
7
  export interface IndexableDocument {
7
8
  /** Memory ID from frontmatter or filename stem */
@@ -83,7 +84,7 @@ async function scanDir(dir: string, memoryRootReal: string): Promise<IndexableDo
83
84
  }
84
85
  }
85
86
  } catch (err) {
86
- if (isNodeError(err) && err.code === "ENOENT") {
87
+ if (isErrnoCode(err, "ENOENT")) {
87
88
  // Optional category directories may not exist yet.
88
89
  return docs;
89
90
  }
@@ -92,10 +93,6 @@ async function scanDir(dir: string, memoryRootReal: string): Promise<IndexableDo
92
93
  return docs;
93
94
  }
94
95
 
95
- function isNodeError(err: unknown): err is NodeJS.ErrnoException {
96
- return typeof err === "object" && err !== null && "code" in err;
97
- }
98
-
99
96
  /**
100
97
  * Scan every recall category subdir of memoryDir for indexable markdown
101
98
  * documents. The directory set is derived from `RECALL_FALLBACK_DIRS`
@@ -114,7 +111,7 @@ export async function scanMemoryDir(memoryDir: string): Promise<IndexableDocumen
114
111
  try {
115
112
  memoryRootReal = await realpath(memoryDir);
116
113
  } catch (err) {
117
- if (isNodeError(err) && err.code === "ENOENT") {
114
+ if (isErrnoCode(err, "ENOENT")) {
118
115
  return [];
119
116
  }
120
117
  throw err;
@@ -6,6 +6,7 @@ import path from "node:path";
6
6
  import { setTimeout as sleep } from "node:timers/promises";
7
7
  import { StorageManager } from "./storage.js";
8
8
  import type { MemoryFile, MemoryLink } from "./types.js";
9
+ import { isErrnoCode } from "./utils/errno.js";
9
10
 
10
11
  export interface SemanticRulePromotionCandidate {
11
12
  id: string;
@@ -79,10 +80,6 @@ function promotionLockHeartbeatMs(): number {
79
80
  return testHooks?.heartbeatMs ?? PROMOTION_LOCK_HEARTBEAT_MS;
80
81
  }
81
82
 
82
- function isErrnoCode(err: unknown, code: string): boolean {
83
- return typeof err === "object" && err !== null && "code" in err && (err as { code?: unknown }).code === code;
84
- }
85
-
86
83
  function promotionLockDir(memoryDir: string, ruleKey: string): string {
87
84
  const digest = createHash("sha256").update(ruleKey).digest("hex");
88
85
  return path.join(path.resolve(memoryDir), "state", "semantic-rule-promotion-locks", `${digest}.lock`);
@@ -0,0 +1,31 @@
1
+ import assert from "node:assert/strict";
2
+ import test from "node:test";
3
+
4
+ import { isErrnoCode, isNotFoundError } from "./errno.js";
5
+
6
+ /** Shapes accepted by every local helper this module replaced (issue #2795). */
7
+ test("isErrnoCode matches code-carrying errors and rejects everything else", () => {
8
+ const enoent = Object.assign(new Error("no such file"), { code: "ENOENT" });
9
+ assert.equal(isErrnoCode(enoent, "ENOENT"), true);
10
+ assert.equal(isErrnoCode({ code: "ENOENT" }, "ENOENT"), true, "plain objects with a code match");
11
+ assert.equal(isErrnoCode(enoent, "EEXIST"), false, "different code does not match");
12
+ assert.equal(isErrnoCode(new Error("no code"), "ENOENT"), false);
13
+ assert.equal(isErrnoCode(null, "ENOENT"), false);
14
+ assert.equal(isErrnoCode(undefined, "ENOENT"), false);
15
+ assert.equal(isErrnoCode("ENOENT", "ENOENT"), false);
16
+ assert.equal(isErrnoCode({}, "ENOENT"), false);
17
+ });
18
+
19
+ test("isNotFoundError is equivalent to isErrnoCode(error, \"ENOENT\")", () => {
20
+ const enoent = Object.assign(new Error("no such file"), { code: "ENOENT" });
21
+ const eexist = Object.assign(new Error("file exists"), { code: "EEXIST" });
22
+ for (const candidate of [enoent, eexist, { code: "ENOENT" }, {}, null, undefined, "ENOENT", 42]) {
23
+ assert.equal(
24
+ isNotFoundError(candidate),
25
+ isErrnoCode(candidate, "ENOENT"),
26
+ `isNotFoundError must agree with isErrnoCode(_, "ENOENT") for ${JSON.stringify(candidate) ?? String(candidate)}`,
27
+ );
28
+ }
29
+ assert.equal(isNotFoundError(enoent), true);
30
+ assert.equal(isNotFoundError(eexist), false);
31
+ });
@@ -4,3 +4,8 @@ export function isErrnoCode(error: unknown, code: string): boolean {
4
4
  && "code" in error
5
5
  && (error as { code?: unknown }).code === code;
6
6
  }
7
+
8
+ /** True iff `error` carries Node's `ENOENT` code (missing file or directory). */
9
+ export function isNotFoundError(error: unknown): boolean {
10
+ return isErrnoCode(error, "ENOENT");
11
+ }
@@ -18,6 +18,7 @@ export {
18
18
  export {
19
19
  builtInConnectorPackageSpecifier,
20
20
  registerWearableConnector,
21
+ selfRegisterWearableConnector,
21
22
  getWearableConnector,
22
23
  listWearableConnectors,
23
24
  clearWearableConnectors,
@@ -64,6 +64,29 @@ export function getWearableConnector(
64
64
  return registrations.get(key);
65
65
  }
66
66
 
67
+ /**
68
+ * Register a connector package with this registry immediately (idempotent)
69
+ * and return its `ensure*Registered()` companion.
70
+ *
71
+ * Connector packages call this once at module scope with their registration
72
+ * record, so importing the module registers the connector as a side effect.
73
+ * The returned companion re-checks the live registry on every call — so it
74
+ * also re-registers after a test-only registry reset — and returns false
75
+ * while the connector stays registered. `registerWearableConnector` throws
76
+ * on duplicate ids, which is why the registry is checked before each call.
77
+ */
78
+ export function selfRegisterWearableConnector(
79
+ registration: WearableConnectorRegistration,
80
+ ): () => boolean {
81
+ const ensureRegistered = (): boolean => {
82
+ if (getWearableConnector(registration.id) !== undefined) return false;
83
+ registerWearableConnector(registration);
84
+ return true;
85
+ };
86
+ ensureRegistered();
87
+ return ensureRegistered;
88
+ }
89
+
67
90
  export function listWearableConnectors(): string[] {
68
91
  return [...registrations.keys()];
69
92
  }