@remnic/core 9.50.2 → 9.51.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/access-admin-ops-surface.d.ts +13 -11
- package/dist/access-admin-ops-surface.js +41 -39
- package/dist/access-authorization-probe.d.ts +13 -11
- package/dist/access-authorization-probe.js +42 -40
- package/dist/access-boundary.d.ts +13 -11
- package/dist/access-boundary.js +41 -39
- package/dist/access-cli.js +109 -104
- package/dist/access-cli.js.map +1 -1
- package/dist/access-coding-context-resolution.d.ts +3 -1
- package/dist/access-extraction-force-flush.d.ts +13 -11
- package/dist/access-extraction-force-flush.js +41 -39
- package/dist/access-health-types.d.ts +3 -1
- package/dist/access-http-lcm-compaction.d.ts +13 -11
- package/dist/access-http-lifecycle-flush.d.ts +13 -11
- package/dist/access-http-offline-stream.d.ts +13 -11
- package/dist/access-http-query.js +41 -39
- package/dist/access-http.d.ts +13 -11
- package/dist/access-http.js +52 -50
- package/dist/access-identity-continuity-surface.d.ts +11 -9
- package/dist/access-identity-continuity-surface.js +41 -39
- package/dist/access-lcm-surface.d.ts +13 -11
- package/dist/access-lcm-surface.js +41 -39
- package/dist/access-mcp.d.ts +13 -11
- package/dist/access-mcp.js +47 -45
- package/dist/access-memory-search-fanout.d.ts +4 -2
- package/dist/{access-namespace-preflight-Dj2QolFE.d.ts → access-namespace-preflight-Ds6CGlCP.d.ts} +1 -1
- package/dist/access-namespace-preflight.d.ts +5 -3
- package/dist/access-namespace-preflight.js +41 -39
- package/dist/access-observe-write-surface.d.ts +13 -11
- package/dist/access-observe-write-surface.js +41 -39
- package/dist/access-offline-manifest.d.ts +11 -9
- package/dist/access-operations-batch.js +43 -41
- package/dist/access-operations.d.ts +13 -11
- package/dist/access-operations.js +46 -44
- package/dist/access-recall-concurrency.d.ts +13 -11
- package/dist/access-recall-concurrency.js +41 -39
- package/dist/access-recall-response.d.ts +13 -11
- package/dist/access-recall-response.js +41 -39
- package/dist/access-recall-surface.d.ts +13 -11
- package/dist/access-recall-surface.js +41 -39
- package/dist/access-schema.js +3 -3
- package/dist/{access-service-DesbnTSa.d.ts → access-service-BY0KJ44c.d.ts} +7 -7
- package/dist/access-service-helpers.d.ts +13 -11
- package/dist/access-service.d.ts +13 -11
- package/dist/access-service.js +41 -39
- package/dist/access-surface-catalog.d.ts +13 -11
- package/dist/access-wearables-meetings-surface.d.ts +5 -3
- package/dist/action-confidence.d.ts +3 -1
- package/dist/active-memory-bridge.d.ts +3 -1
- package/dist/active-recall.d.ts +3 -1
- package/dist/active-recall.js +5 -3
- package/dist/active-recall.js.map +1 -1
- package/dist/adapters/index.js +4 -4
- package/dist/adapters/registry.js +2 -2
- package/dist/ambient-provenance.d.ts +3 -1
- package/dist/archive-mutation-version.d.ts +9 -0
- package/dist/archive-mutation-version.js +20 -0
- package/dist/artifact-search.d.ts +3 -1
- package/dist/behavior-learner.d.ts +3 -1
- package/dist/behavior-signals.d.ts +3 -1
- package/dist/bootstrap.d.ts +11 -9
- package/dist/briefing.d.ts +4 -2
- package/dist/briefing.js +10 -9
- package/dist/buffer-surprise-report.d.ts +3 -1
- package/dist/buffer-turn-helpers.d.ts +3 -1
- package/dist/buffer.d.ts +4 -2
- package/dist/buffer.js +5 -5
- package/dist/bulk-import/index.d.ts +5 -3
- package/dist/calibration.d.ts +3 -1
- package/dist/capabilities.d.ts +3 -1
- package/dist/{catalog-D-G7RgXR.d.ts → catalog-D3B4RDy1.d.ts} +1 -1
- package/dist/causal-behavior.d.ts +3 -1
- package/dist/causal-behavior.js +2 -2
- package/dist/causal-chain.js +2 -2
- package/dist/causal-consolidation.d.ts +3 -1
- package/dist/causal-consolidation.js +13 -12
- package/dist/causal-consolidation.js.map +1 -1
- package/dist/causal-retrieval.js +2 -2
- package/dist/causal-trajectory-graph.d.ts +4 -2
- package/dist/causal-trajectory-graph.js +2 -1
- package/dist/causal-trajectory-graph.js.map +1 -1
- package/dist/causal-trajectory.js +1 -1
- package/dist/{chunk-KDG2KTWW.js → chunk-33SV3E43.js} +4 -4
- package/dist/{chunk-2HGUDBRJ.js → chunk-37ZO6LLJ.js} +2 -2
- package/dist/{chunk-QW3WFHKU.js → chunk-45BRYON6.js} +2 -2
- package/dist/{chunk-GZICBRWK.js → chunk-4F6X3RXW.js} +2 -2
- package/dist/{chunk-7BAYBYY5.js → chunk-4PC4PRJE.js} +2 -2
- package/dist/{chunk-VJXY5ZCT.js → chunk-52UKFTUK.js} +2 -2
- package/dist/{chunk-ESG7Z255.js → chunk-5UDMFE3Q.js} +2 -2
- package/dist/{chunk-JPHEOE6Z.js → chunk-6MTSFX7A.js} +15 -15
- package/dist/chunk-6ZN34ISG.js +44 -0
- package/dist/chunk-6ZN34ISG.js.map +1 -0
- package/dist/{chunk-M4MP34AQ.js → chunk-AHZOMHWN.js} +1 -1
- package/dist/{chunk-Z3RHPGSY.js → chunk-AIUBBHSF.js} +3 -3
- package/dist/{chunk-S3AYIQCU.js → chunk-AXIDQG5A.js} +12 -12
- package/dist/{chunk-QN7NTKRC.js → chunk-AZ2QBGYB.js} +1 -1
- package/dist/{chunk-47J4EDGR.js → chunk-AZM4CCAC.js} +8 -8
- package/dist/{chunk-IXXABW5A.js → chunk-BHXYAVUM.js} +11 -5
- package/dist/chunk-BHXYAVUM.js.map +1 -0
- package/dist/{chunk-L2DPF4DF.js → chunk-BIJAWZYW.js} +54 -12
- package/dist/chunk-BIJAWZYW.js.map +1 -0
- package/dist/{chunk-LEJPSMKM.js → chunk-C5QLI33R.js} +3 -3
- package/dist/{chunk-SV3PSA7Y.js → chunk-CV6BBVYV.js} +5 -5
- package/dist/{chunk-V7X767RT.js → chunk-DCZBSE4F.js} +52 -52
- package/dist/chunk-FC67T4E6.js +70 -0
- package/dist/chunk-FC67T4E6.js.map +1 -0
- package/dist/{chunk-7PKFPLLZ.js → chunk-FXTYIA46.js} +2 -2
- package/dist/{chunk-64BHFFKZ.js → chunk-HLYR2TQL.js} +5 -5
- package/dist/{chunk-5C2HNJMO.js → chunk-J5LLX6IL.js} +32 -32
- package/dist/{chunk-RKNJBZ55.js → chunk-JBPKEARU.js} +4 -4
- package/dist/{chunk-PLKFO2HJ.js → chunk-JL43BVDE.js} +2 -2
- package/dist/{chunk-2S72LWKX.js → chunk-JYL3BVVZ.js} +2 -2
- package/dist/{chunk-IPLYGWQF.js → chunk-KQAFEZQX.js} +5 -5
- package/dist/chunk-LXY5VVGM.js +61 -0
- package/dist/chunk-LXY5VVGM.js.map +1 -0
- package/dist/{chunk-PYKKWQZ2.js → chunk-M7BXDKPR.js} +6 -6
- package/dist/{chunk-Z54EM5YZ.js → chunk-MAXVH44E.js} +7 -7
- package/dist/{chunk-LYMNZZIM.js → chunk-NIS256NW.js} +2 -2
- package/dist/{chunk-67QG75MJ.js → chunk-NLK2VZYZ.js} +2 -2
- package/dist/{chunk-A4QMKFFO.js → chunk-O5FFBO2M.js} +14 -28
- package/dist/chunk-O5FFBO2M.js.map +1 -0
- package/dist/{chunk-JYIFGGEM.js → chunk-OUKBMQ2O.js} +2 -2
- package/dist/{chunk-75XOWNRS.js → chunk-OYESWJ43.js} +4 -4
- package/dist/{chunk-TS4AJ2GI.js → chunk-PA45XCUD.js} +3 -3
- package/dist/{chunk-BJYET5TX.js → chunk-PRDJMOST.js} +7 -1
- package/dist/chunk-PRDJMOST.js.map +1 -0
- package/dist/{chunk-4MBPIL4V.js → chunk-PUSLMZBQ.js} +2 -2
- package/dist/{chunk-RVO6TCTU.js → chunk-QCECHYZL.js} +6 -6
- package/dist/{chunk-GFIKG4FR.js → chunk-QGR6OVGT.js} +2 -2
- package/dist/{chunk-NSGU76YO.js → chunk-QHFV6VNU.js} +6 -2
- package/dist/chunk-QHFV6VNU.js.map +1 -0
- package/dist/{chunk-PDEKQWDV.js → chunk-QT2FRYI4.js} +18 -2
- package/dist/chunk-QT2FRYI4.js.map +1 -0
- package/dist/{chunk-HNZKVLAN.js → chunk-S354QO4R.js} +2 -2
- package/dist/{chunk-NO37MR45.js → chunk-SOEN6KCF.js} +2 -2
- package/dist/{chunk-FXX6RQYC.js → chunk-TPTECFWR.js} +2 -2
- package/dist/{chunk-GDDGZVFI.js → chunk-UEVLYVNW.js} +2 -2
- package/dist/{chunk-YQ4IQ2GA.js → chunk-UT5BV5OG.js} +2 -2
- package/dist/{chunk-LAQ33B5D.js → chunk-UU3G6GUP.js} +1 -1
- package/dist/chunk-UU3G6GUP.js.map +1 -0
- package/dist/{chunk-LNTUXKBT.js → chunk-UYYW2KPU.js} +2 -2
- package/dist/{chunk-BOFVT6P3.js → chunk-VBHPOWBJ.js} +175 -98
- package/dist/chunk-VBHPOWBJ.js.map +1 -0
- package/dist/{chunk-QSYL5CXK.js → chunk-VKXWK44Q.js} +3 -3
- package/dist/{chunk-KMWYZTIE.js → chunk-VMMQDEN5.js} +2 -2
- package/dist/{chunk-JB6D7EFB.js → chunk-VVG2BOKA.js} +2 -2
- package/dist/chunk-W5BIQOAJ.js +69 -0
- package/dist/chunk-W5BIQOAJ.js.map +1 -0
- package/dist/{chunk-V5H6OJCR.js → chunk-W5XVQFLM.js} +2 -2
- package/dist/{chunk-OIOZ6MOP.js → chunk-W6FNX2LP.js} +2 -2
- package/dist/{chunk-6QPHF6RR.js → chunk-WQM326GS.js} +2 -2
- package/dist/{chunk-TQFHQPWD.js → chunk-XADV5IZ3.js} +8 -8
- package/dist/{chunk-DATDLJAO.js → chunk-XAPMEU3K.js} +2 -2
- package/dist/chunk-XXSOVESA.js +42 -0
- package/dist/chunk-XXSOVESA.js.map +1 -0
- package/dist/{chunk-IK6X5QPO.js → chunk-ZHY5TMJG.js} +1193 -443
- package/dist/chunk-ZHY5TMJG.js.map +1 -0
- package/dist/{chunk-N3LL5NEU.js → chunk-ZMYDYNI4.js} +2 -2
- package/dist/{cli-D4vvtxjY.d.ts → cli-CnOkH9hA.d.ts} +6 -6
- package/dist/cli.d.ts +15 -13
- package/dist/cli.js +74 -70
- package/dist/coding/pre-action-gate.d.ts +3 -1
- package/dist/coding/pre-action-gate.js +2 -2
- package/dist/compounding/engine.d.ts +4 -2
- package/dist/compounding/engine.js +10 -9
- package/dist/compounding/preference-consolidator.d.ts +3 -1
- package/dist/compression-optimizer.d.ts +3 -1
- package/dist/config.d.ts +3 -1
- package/dist/config.js +5 -3
- package/dist/connectors/codex-materialize-runner.d.ts +3 -1
- package/dist/connectors/codex-materialize-runner.js +10 -9
- package/dist/connectors/codex-materialize.d.ts +3 -1
- package/dist/connectors/index.d.ts +3 -1
- package/dist/connectors/index.js +10 -9
- package/dist/consolidation-provenance-check.d.ts +4 -2
- package/dist/consolidation-undo.d.ts +4 -2
- package/dist/contradiction/index.d.ts +4 -2
- package/dist/contradiction-config.d.ts +29 -0
- package/dist/contradiction-config.js +12 -0
- package/dist/contradiction-config.js.map +1 -0
- package/dist/converge-config.d.ts +3 -1
- package/dist/convergence-refresh.d.ts +4 -2
- package/dist/convergence-refresh.js +12 -11
- package/dist/conversation-index/backend.d.ts +3 -1
- package/dist/conversation-index/chunker.d.ts +3 -1
- package/dist/conversation-index/faiss-adapter.d.ts +3 -1
- package/dist/conversation-index/indexer.d.ts +3 -1
- package/dist/conversation-index/search.d.ts +3 -1
- package/dist/corpus-watermark.d.ts +3 -1
- package/dist/corpus-watermark.js +21 -20
- package/dist/day-summary.d.ts +3 -1
- package/dist/delinearize.d.ts +3 -1
- package/dist/dependency-propagation-config.d.ts +3 -1
- package/dist/direct-answer-wiring.d.ts +3 -1
- package/dist/direct-answer.d.ts +3 -1
- package/dist/embedding-fallback.d.ts +3 -1
- package/dist/enrichment/index.d.ts +3 -1
- package/dist/entity-retrieval.d.ts +4 -2
- package/dist/entity-retrieval.js +10 -9
- package/dist/entity-schema.d.ts +3 -1
- package/dist/explicit-capture.d.ts +11 -9
- package/dist/explicit-capture.js +3 -2
- package/dist/external-wiki-access.d.ts +13 -11
- package/dist/external-wiki-access.js +42 -40
- package/dist/external-wiki-collection-registration.d.ts +3 -1
- package/dist/external-wiki-collection.d.ts +3 -1
- package/dist/external-wiki-mcp-tools.d.ts +13 -11
- package/dist/extraction-error-classification.d.ts +3 -1
- package/dist/extraction-faithfulness.d.ts +3 -1
- package/dist/extraction-judge-telemetry.d.ts +3 -1
- package/dist/extraction-judge-training.d.ts +3 -1
- package/dist/extraction-judge.d.ts +3 -1
- package/dist/extraction-liveness.d.ts +3 -1
- package/dist/extraction-normalization.d.ts +3 -1
- package/dist/extraction-prompt.d.ts +3 -1
- package/dist/extraction-source-grounding-rules.d.ts +3 -1
- package/dist/extraction-source-grounding.d.ts +3 -1
- package/dist/extraction.d.ts +3 -1
- package/dist/extraction.js +22 -21
- package/dist/fallback-llm.d.ts +3 -1
- package/dist/graph-444E-DrF.d.ts +349 -0
- package/dist/graph-dashboard-diff.d.ts +4 -2
- package/dist/graph-dashboard-key.d.ts +4 -2
- package/dist/graph-dashboard-parser.d.ts +4 -2
- package/dist/{graph-edge-decay-Z6ENALU2.js → graph-edge-decay-65KMOJWY.js} +4 -3
- package/dist/graph-edge-decay-65KMOJWY.js.map +1 -0
- package/dist/graph-edge-reinforcement.d.ts +4 -2
- package/dist/graph-path-reconstruction.d.ts +10 -0
- package/dist/graph-path-reconstruction.js +12 -0
- package/dist/graph-path-reconstruction.js.map +1 -0
- package/dist/graph-path-scoring-config.d.ts +8 -0
- package/dist/graph-path-scoring-config.js +10 -0
- package/dist/graph-path-scoring-config.js.map +1 -0
- package/dist/graph-path-scoring.d.ts +36 -0
- package/dist/graph-path-scoring.js +11 -0
- package/dist/graph-path-scoring.js.map +1 -0
- package/dist/graph-snapshot.d.ts +4 -2
- package/dist/graph-snapshot.js +3 -2
- package/dist/graph.d.ts +5 -318
- package/dist/graph.js +5 -1
- package/dist/harmonic-retrieval.js +1 -1
- package/dist/importance.d.ts +3 -1
- package/dist/importers/index.d.ts +3 -1
- package/dist/in-flight-reads.d.ts +3 -1
- package/dist/index.d.ts +22 -20
- package/dist/index.js +149 -144
- package/dist/intent.d.ts +3 -1
- package/dist/lcm/engine.d.ts +3 -1
- package/dist/lcm/engine.js +3 -3
- package/dist/lcm/index.d.ts +3 -1
- package/dist/lcm/index.js +6 -6
- package/dist/lcm/tools.d.ts +3 -1
- package/dist/lifecycle.d.ts +3 -1
- package/dist/live-connectors-runner.d.ts +3 -1
- package/dist/local-llm.d.ts +3 -1
- package/dist/local-model-endpoint.d.ts +3 -1
- package/dist/maintenance/memory-governance.d.ts +3 -1
- package/dist/maintenance/memory-governance.js +10 -9
- package/dist/maintenance/rebuild-memory-lifecycle-ledger.d.ts +4 -2
- package/dist/maintenance/rebuild-memory-lifecycle-ledger.js +10 -9
- package/dist/maintenance/rebuild-memory-projection.d.ts +4 -2
- package/dist/maintenance/rebuild-memory-projection.js +11 -10
- package/dist/{maintenance-ClmUVpGI.d.ts → maintenance-CKwxpdRx.d.ts} +3 -3
- package/dist/mcp-memory-inspector-app.d.ts +13 -11
- package/dist/memory-action-policy.d.ts +3 -1
- package/dist/memory-cache.d.ts +3 -1
- package/dist/memory-lifecycle-ledger-utils.d.ts +3 -1
- package/dist/memory-projection-store.d.ts +3 -1
- package/dist/memory-provenance.d.ts +3 -1
- package/dist/memory-snapshot.d.ts +3 -1
- package/dist/memory-worth-outcomes.d.ts +4 -2
- package/dist/models-json.d.ts +3 -1
- package/dist/namespaces/migrate.d.ts +5 -3
- package/dist/namespaces/migrate.js +20 -19
- package/dist/namespaces/principal.d.ts +3 -1
- package/dist/namespaces/search.d.ts +3 -1
- package/dist/namespaces/search.js +7 -7
- package/dist/namespaces/storage.d.ts +5 -3
- package/dist/namespaces/storage.js +10 -9
- package/dist/native-knowledge.d.ts +3 -1
- package/dist/offline-sync-impression-drain.d.ts +3 -1
- package/dist/operator-doctor-corpus.d.ts +3 -1
- package/dist/operator-doctor-corpus.js +22 -21
- package/dist/operator-doctor-replica.d.ts +3 -1
- package/dist/operator-toolkit.d.ts +6 -4
- package/dist/operator-toolkit.js +33 -29
- package/dist/orchestration/compression-guideline-coordinator.d.ts +4 -2
- package/dist/orchestration/maintenance.d.ts +6 -4
- package/dist/orchestration/maintenance.js +15 -14
- package/dist/{orchestrator-qJ07zI8H.d.ts → orchestrator-BshGam-o.d.ts} +45 -19
- package/dist/orchestrator.d.ts +11 -9
- package/dist/orchestrator.js +109 -104
- package/dist/patterns-cli.d.ts +3 -1
- package/dist/{pipeline-WFCxhHOn.d.ts → pipeline-D21Rs6gW.d.ts} +1 -1
- package/dist/policy-runtime.d.ts +3 -1
- package/dist/proactive-contention.d.ts +3 -1
- package/dist/provenance.d.ts +3 -1
- package/dist/{qmd-5tzkQ44y.d.ts → qmd-Dhle1P4X.d.ts} +1 -1
- package/dist/qmd-preflight.d.ts +4 -2
- package/dist/qmd-recall-cache.d.ts +3 -1
- package/dist/qmd.d.ts +4 -2
- package/dist/qmd.js +4 -4
- package/dist/recall-concurrency-config.d.ts +3 -1
- package/dist/recall-disclosure-escalation.d.ts +3 -1
- package/dist/recall-explain-renderer.d.ts +3 -1
- package/dist/recall-explain-renderer.js +3 -3
- package/dist/recall-memory-map.d.ts +3 -1
- package/dist/recall-planner-llm.d.ts +3 -1
- package/dist/recall-planner-llm.js +3 -3
- package/dist/recall-state.d.ts +7 -1
- package/dist/recall-state.js +1 -1
- package/dist/recall-tag-filter.d.ts +3 -1
- package/dist/recall-timings.d.ts +3 -1
- package/dist/recall-xray-cli.d.ts +3 -1
- package/dist/recall-xray-cli.js +4 -4
- package/dist/recall-xray-renderer.d.ts +3 -1
- package/dist/recall-xray-renderer.js +3 -3
- package/dist/recall-xray.d.ts +7 -1
- package/dist/recall-xray.js +2 -2
- package/dist/reconcile/cursor.d.ts +3 -1
- package/dist/reconcile/manifest.d.ts +3 -1
- package/dist/reconcile/plan.d.ts +3 -1
- package/dist/replay/normalizers/chatgpt.d.ts +3 -1
- package/dist/replay/normalizers/claude.d.ts +3 -1
- package/dist/replay/normalizers/openclaw.d.ts +3 -1
- package/dist/replay/normalizers/shared.d.ts +3 -1
- package/dist/replay/runner.d.ts +3 -1
- package/dist/replay/types.d.ts +3 -1
- package/dist/replica-divergence.d.ts +3 -1
- package/dist/replica-peers-config.d.ts +3 -1
- package/dist/resolve-auth-token.d.ts +3 -1
- package/dist/resume-bundles.js +6 -4
- package/dist/retrieval-agents.d.ts +4 -2
- package/dist/retrieval-tiers.d.ts +3 -1
- package/dist/routing/engine.d.ts +3 -1
- package/dist/routing/store.d.ts +3 -1
- package/dist/salvage-envelope.d.ts +3 -1
- package/dist/{scope-profiles--vfXPl3X.d.ts → scope-profiles-NzGPDXLn.d.ts} +1 -1
- package/dist/search/embed-helper.d.ts +3 -1
- package/dist/search/factory.d.ts +3 -1
- package/dist/search/factory.js +6 -6
- package/dist/search/index.d.ts +3 -1
- package/dist/search/index.js +12 -12
- package/dist/search/lancedb-backend.d.ts +3 -1
- package/dist/search/meilisearch-backend.d.ts +3 -1
- package/dist/search/noop-backend.d.ts +3 -1
- package/dist/search/orama-backend.d.ts +3 -1
- package/dist/search/port.d.ts +3 -1
- package/dist/search/remote-backend.d.ts +3 -1
- package/dist/{semantic-consolidation-BBDuP9nJ.d.ts → semantic-consolidation-DLDKvyy5.d.ts} +1 -1
- package/dist/semantic-consolidation.d.ts +4 -2
- package/dist/semantic-consolidation.js +11 -10
- package/dist/semantic-rule-promotion.js +10 -9
- package/dist/semantic-rule-verifier.d.ts +3 -1
- package/dist/semantic-rule-verifier.js +10 -9
- package/dist/{service-B8DtbpCM.d.ts → service-BIgVM7fL.d.ts} +2 -2
- package/dist/session-observer-bands.d.ts +3 -1
- package/dist/session-observer-state.d.ts +3 -1
- package/dist/shared-context/manager.d.ts +3 -1
- package/dist/signal.d.ts +3 -1
- package/dist/source-agent-qualifier.d.ts +3 -1
- package/dist/source-agent-qualifier.js +18 -17
- package/dist/{storage-BkYN1RIy.d.ts → storage-CVfGWqCI.d.ts} +7 -6
- package/dist/storage.d.ts +4 -2
- package/dist/storage.js +9 -8
- package/dist/summarizer.d.ts +3 -1
- package/dist/summary-snapshot.d.ts +3 -1
- package/dist/temporal-supersession.d.ts +4 -2
- package/dist/temporal-timeline-recall.d.ts +3 -1
- package/dist/temporal-validity.d.ts +3 -1
- package/dist/threading.d.ts +3 -1
- package/dist/tier-migration.d.ts +4 -2
- package/dist/tier-routing.d.ts +3 -1
- package/dist/topics.d.ts +3 -1
- package/dist/transcript.d.ts +3 -1
- package/dist/transfer/autodetect.js +1 -1
- package/dist/transfer/backup.js +1 -1
- package/dist/transfer/capsule-export.js +2 -2
- package/dist/trust-score-stage.d.ts +3 -1
- package/dist/trust-score.d.ts +3 -1
- package/dist/{types-u2s9j1uD.d.ts → types-CkiDUorT.d.ts} +10 -16
- package/dist/types.d.ts +3 -1
- package/dist/types.js +1 -1
- package/dist/utility-runtime.d.ts +3 -1
- package/dist/verified-recall.js +10 -9
- package/dist/write-envelope.d.ts +3 -1
- package/package.json +2 -2
- package/src/archive-mutation-version.ts +59 -0
- package/src/config.test.ts +45 -0
- package/src/config.ts +10 -30
- package/src/contradiction/contradiction.test.ts +86 -1
- package/src/contradiction-config.ts +92 -0
- package/src/graph-path-reconstruction.ts +91 -0
- package/src/graph-path-scoring-config.ts +55 -0
- package/src/graph-path-scoring.test.ts +238 -0
- package/src/graph-path-scoring.ts +77 -0
- package/src/graph.test.ts +225 -5
- package/src/graph.ts +72 -5
- package/src/orchestration/contradiction-linking-coordinator.ts +246 -76
- package/src/orchestration/contradiction-localization.integration.test.ts +1953 -0
- package/src/orchestration/extraction-anchor-snapshot.ts +83 -0
- package/src/orchestration/extraction-persist-deps.ts +8 -2
- package/src/orchestration/extraction-persist.ts +43 -34
- package/src/orchestration/graph-path-state-loader.test.ts +801 -0
- package/src/orchestration/graph-path-state-loader.ts +318 -0
- package/src/orchestration/graph-recall-coordinator.integration.test.ts +1163 -0
- package/src/orchestration/graph-recall-coordinator.ts +206 -29
- package/src/orchestration/graph-recall-seam.ts +19 -0
- package/src/orchestration/recall-internal-deps.ts +7 -13
- package/src/orchestration/recall-internal.ts +5 -0
- package/src/orchestration/recall-introspection.ts +9 -1
- package/src/orchestration/recall-search-pipeline.ts +8 -13
- package/src/orchestration/update-localization.test.ts +784 -0
- package/src/orchestration/update-localization.ts +173 -0
- package/src/orchestrator.ts +19 -18
- package/src/recall-state.test.ts +29 -1
- package/src/recall-state.ts +13 -0
- package/src/recall-xray-renderer.test.ts +45 -0
- package/src/recall-xray-renderer.ts +16 -0
- package/src/recall-xray.ts +13 -0
- package/src/storage/supersession-side-effects.ts +97 -0
- package/src/storage/tombstone-blocked-capture-sync.ts +13 -5
- package/src/storage-contract/cache-coherence.test.ts +299 -0
- package/src/storage.ts +86 -88
- package/src/types.ts +12 -15
- package/dist/chunk-A4QMKFFO.js.map +0 -1
- package/dist/chunk-BJYET5TX.js.map +0 -1
- package/dist/chunk-BOFVT6P3.js.map +0 -1
- package/dist/chunk-IK6X5QPO.js.map +0 -1
- package/dist/chunk-IXXABW5A.js.map +0 -1
- package/dist/chunk-L2DPF4DF.js.map +0 -1
- package/dist/chunk-LAQ33B5D.js.map +0 -1
- package/dist/chunk-NSGU76YO.js.map +0 -1
- package/dist/chunk-PDEKQWDV.js.map +0 -1
- /package/dist/{graph-edge-decay-Z6ENALU2.js.map → archive-mutation-version.js.map} +0 -0
- /package/dist/{chunk-KDG2KTWW.js.map → chunk-33SV3E43.js.map} +0 -0
- /package/dist/{chunk-2HGUDBRJ.js.map → chunk-37ZO6LLJ.js.map} +0 -0
- /package/dist/{chunk-QW3WFHKU.js.map → chunk-45BRYON6.js.map} +0 -0
- /package/dist/{chunk-GZICBRWK.js.map → chunk-4F6X3RXW.js.map} +0 -0
- /package/dist/{chunk-7BAYBYY5.js.map → chunk-4PC4PRJE.js.map} +0 -0
- /package/dist/{chunk-VJXY5ZCT.js.map → chunk-52UKFTUK.js.map} +0 -0
- /package/dist/{chunk-ESG7Z255.js.map → chunk-5UDMFE3Q.js.map} +0 -0
- /package/dist/{chunk-JPHEOE6Z.js.map → chunk-6MTSFX7A.js.map} +0 -0
- /package/dist/{chunk-M4MP34AQ.js.map → chunk-AHZOMHWN.js.map} +0 -0
- /package/dist/{chunk-Z3RHPGSY.js.map → chunk-AIUBBHSF.js.map} +0 -0
- /package/dist/{chunk-S3AYIQCU.js.map → chunk-AXIDQG5A.js.map} +0 -0
- /package/dist/{chunk-QN7NTKRC.js.map → chunk-AZ2QBGYB.js.map} +0 -0
- /package/dist/{chunk-47J4EDGR.js.map → chunk-AZM4CCAC.js.map} +0 -0
- /package/dist/{chunk-LEJPSMKM.js.map → chunk-C5QLI33R.js.map} +0 -0
- /package/dist/{chunk-SV3PSA7Y.js.map → chunk-CV6BBVYV.js.map} +0 -0
- /package/dist/{chunk-V7X767RT.js.map → chunk-DCZBSE4F.js.map} +0 -0
- /package/dist/{chunk-7PKFPLLZ.js.map → chunk-FXTYIA46.js.map} +0 -0
- /package/dist/{chunk-64BHFFKZ.js.map → chunk-HLYR2TQL.js.map} +0 -0
- /package/dist/{chunk-5C2HNJMO.js.map → chunk-J5LLX6IL.js.map} +0 -0
- /package/dist/{chunk-RKNJBZ55.js.map → chunk-JBPKEARU.js.map} +0 -0
- /package/dist/{chunk-PLKFO2HJ.js.map → chunk-JL43BVDE.js.map} +0 -0
- /package/dist/{chunk-2S72LWKX.js.map → chunk-JYL3BVVZ.js.map} +0 -0
- /package/dist/{chunk-IPLYGWQF.js.map → chunk-KQAFEZQX.js.map} +0 -0
- /package/dist/{chunk-PYKKWQZ2.js.map → chunk-M7BXDKPR.js.map} +0 -0
- /package/dist/{chunk-Z54EM5YZ.js.map → chunk-MAXVH44E.js.map} +0 -0
- /package/dist/{chunk-LYMNZZIM.js.map → chunk-NIS256NW.js.map} +0 -0
- /package/dist/{chunk-67QG75MJ.js.map → chunk-NLK2VZYZ.js.map} +0 -0
- /package/dist/{chunk-JYIFGGEM.js.map → chunk-OUKBMQ2O.js.map} +0 -0
- /package/dist/{chunk-75XOWNRS.js.map → chunk-OYESWJ43.js.map} +0 -0
- /package/dist/{chunk-TS4AJ2GI.js.map → chunk-PA45XCUD.js.map} +0 -0
- /package/dist/{chunk-4MBPIL4V.js.map → chunk-PUSLMZBQ.js.map} +0 -0
- /package/dist/{chunk-RVO6TCTU.js.map → chunk-QCECHYZL.js.map} +0 -0
- /package/dist/{chunk-GFIKG4FR.js.map → chunk-QGR6OVGT.js.map} +0 -0
- /package/dist/{chunk-HNZKVLAN.js.map → chunk-S354QO4R.js.map} +0 -0
- /package/dist/{chunk-NO37MR45.js.map → chunk-SOEN6KCF.js.map} +0 -0
- /package/dist/{chunk-FXX6RQYC.js.map → chunk-TPTECFWR.js.map} +0 -0
- /package/dist/{chunk-GDDGZVFI.js.map → chunk-UEVLYVNW.js.map} +0 -0
- /package/dist/{chunk-YQ4IQ2GA.js.map → chunk-UT5BV5OG.js.map} +0 -0
- /package/dist/{chunk-LNTUXKBT.js.map → chunk-UYYW2KPU.js.map} +0 -0
- /package/dist/{chunk-QSYL5CXK.js.map → chunk-VKXWK44Q.js.map} +0 -0
- /package/dist/{chunk-KMWYZTIE.js.map → chunk-VMMQDEN5.js.map} +0 -0
- /package/dist/{chunk-JB6D7EFB.js.map → chunk-VVG2BOKA.js.map} +0 -0
- /package/dist/{chunk-V5H6OJCR.js.map → chunk-W5XVQFLM.js.map} +0 -0
- /package/dist/{chunk-OIOZ6MOP.js.map → chunk-W6FNX2LP.js.map} +0 -0
- /package/dist/{chunk-6QPHF6RR.js.map → chunk-WQM326GS.js.map} +0 -0
- /package/dist/{chunk-TQFHQPWD.js.map → chunk-XADV5IZ3.js.map} +0 -0
- /package/dist/{chunk-DATDLJAO.js.map → chunk-XAPMEU3K.js.map} +0 -0
- /package/dist/{chunk-N3LL5NEU.js.map → chunk-ZMYDYNI4.js.map} +0 -0
|
@@ -13,7 +13,7 @@ import {
|
|
|
13
13
|
import {
|
|
14
14
|
ActivityStore,
|
|
15
15
|
MaintenanceScheduler
|
|
16
|
-
} from "./chunk-
|
|
16
|
+
} from "./chunk-OYESWJ43.js";
|
|
17
17
|
import {
|
|
18
18
|
runPeerProfileReasoner
|
|
19
19
|
} from "./chunk-I74SUMNI.js";
|
|
@@ -22,7 +22,7 @@ import {
|
|
|
22
22
|
} from "./chunk-7HYPN2GC.js";
|
|
23
23
|
import {
|
|
24
24
|
LcmEngine
|
|
25
|
-
} from "./chunk-
|
|
25
|
+
} from "./chunk-MAXVH44E.js";
|
|
26
26
|
import {
|
|
27
27
|
chunkTranscriptEntries
|
|
28
28
|
} from "./chunk-TECVW3JP.js";
|
|
@@ -32,7 +32,7 @@ import {
|
|
|
32
32
|
import {
|
|
33
33
|
CompoundingEngine,
|
|
34
34
|
defaultTierMigrationCycleBudget
|
|
35
|
-
} from "./chunk-
|
|
35
|
+
} from "./chunk-UT5BV5OG.js";
|
|
36
36
|
import {
|
|
37
37
|
SharedContextManager
|
|
38
38
|
} from "./chunk-M23RF3LJ.js";
|
|
@@ -41,12 +41,6 @@ import {
|
|
|
41
41
|
applyUtilityRankingRuntimeDelta,
|
|
42
42
|
loadUtilityRuntimeValues
|
|
43
43
|
} from "./chunk-SEF4IOFE.js";
|
|
44
|
-
import {
|
|
45
|
-
TierMigrationExecutor
|
|
46
|
-
} from "./chunk-YRFAYOFQ.js";
|
|
47
|
-
import {
|
|
48
|
-
decideTierTransition
|
|
49
|
-
} from "./chunk-S75M5ZRK.js";
|
|
50
44
|
import {
|
|
51
45
|
TmtBuilder
|
|
52
46
|
} from "./chunk-ECZU5BJH.js";
|
|
@@ -59,6 +53,12 @@ import {
|
|
|
59
53
|
import {
|
|
60
54
|
CODEX_THREAD_KEY_PREFIX
|
|
61
55
|
} from "./chunk-4EX5WZ4M.js";
|
|
56
|
+
import {
|
|
57
|
+
TierMigrationExecutor
|
|
58
|
+
} from "./chunk-YRFAYOFQ.js";
|
|
59
|
+
import {
|
|
60
|
+
decideTierTransition
|
|
61
|
+
} from "./chunk-S75M5ZRK.js";
|
|
62
62
|
import {
|
|
63
63
|
HourlySummarizer
|
|
64
64
|
} from "./chunk-LLJMAULE.js";
|
|
@@ -69,6 +69,14 @@ import {
|
|
|
69
69
|
import {
|
|
70
70
|
SessionObserverState
|
|
71
71
|
} from "./chunk-QFN4U7AG.js";
|
|
72
|
+
import {
|
|
73
|
+
applyRuntimeRetrievalPolicy
|
|
74
|
+
} from "./chunk-5IZL4DCV.js";
|
|
75
|
+
import {
|
|
76
|
+
RerankCache,
|
|
77
|
+
reorderByRankedKeys,
|
|
78
|
+
rerankLocalOrNoop
|
|
79
|
+
} from "./chunk-LUDXM7MD.js";
|
|
72
80
|
import {
|
|
73
81
|
buildResponseGuidanceRecallSection,
|
|
74
82
|
shouldRecallResponseGuidance
|
|
@@ -94,26 +102,12 @@ import {
|
|
|
94
102
|
recencyWindowFromPrompt,
|
|
95
103
|
resolvePromptTagPrefilterAsync
|
|
96
104
|
} from "./chunk-ZOKZIR5K.js";
|
|
97
|
-
import {
|
|
98
|
-
applyRuntimeRetrievalPolicy
|
|
99
|
-
} from "./chunk-5IZL4DCV.js";
|
|
100
105
|
import {
|
|
101
106
|
findUnresolvedEntityRefs
|
|
102
107
|
} from "./chunk-X7XN6YU4.js";
|
|
103
108
|
import {
|
|
104
109
|
RelevanceStore
|
|
105
110
|
} from "./chunk-KATEWTQJ.js";
|
|
106
|
-
import {
|
|
107
|
-
RerankCache,
|
|
108
|
-
reorderByRankedKeys,
|
|
109
|
-
rerankLocalOrNoop
|
|
110
|
-
} from "./chunk-LUDXM7MD.js";
|
|
111
|
-
import {
|
|
112
|
-
LastRecallStore,
|
|
113
|
-
RecallHandleHistoryStore,
|
|
114
|
-
TierMigrationStatusStore,
|
|
115
|
-
clampGraphRecallExpandedEntries
|
|
116
|
-
} from "./chunk-BJYET5TX.js";
|
|
117
111
|
import {
|
|
118
112
|
dedupeResultsByNamespace,
|
|
119
113
|
hasMemoryForResult,
|
|
@@ -125,6 +119,12 @@ import {
|
|
|
125
119
|
import {
|
|
126
120
|
reorderRecallResultsWithMmr
|
|
127
121
|
} from "./chunk-YDBIWGNI.js";
|
|
122
|
+
import {
|
|
123
|
+
LastRecallStore,
|
|
124
|
+
RecallHandleHistoryStore,
|
|
125
|
+
TierMigrationStatusStore,
|
|
126
|
+
clampGraphRecallExpandedEntries
|
|
127
|
+
} from "./chunk-PRDJMOST.js";
|
|
128
128
|
import {
|
|
129
129
|
applyReasoningTraceBoost
|
|
130
130
|
} from "./chunk-ZZTOURJI.js";
|
|
@@ -144,6 +144,12 @@ import {
|
|
|
144
144
|
import {
|
|
145
145
|
runLiveConnectorsOnce
|
|
146
146
|
} from "./chunk-HTIIXNJQ.js";
|
|
147
|
+
import {
|
|
148
|
+
classifyMemoryKind
|
|
149
|
+
} from "./chunk-YAZNBMNF.js";
|
|
150
|
+
import {
|
|
151
|
+
scoreEvidencePathDetail
|
|
152
|
+
} from "./chunk-XXSOVESA.js";
|
|
147
153
|
import {
|
|
148
154
|
deriveHarmonicRecords,
|
|
149
155
|
harmonicEntityReferenceMatches,
|
|
@@ -151,16 +157,13 @@ import {
|
|
|
151
157
|
normalizedHarmonicEntityIdentity,
|
|
152
158
|
persistHarmonicRecords
|
|
153
159
|
} from "./chunk-GXSOUIA4.js";
|
|
154
|
-
import {
|
|
155
|
-
classifyMemoryKind
|
|
156
|
-
} from "./chunk-YAZNBMNF.js";
|
|
157
160
|
import {
|
|
158
161
|
buildFocusedListRecallSection,
|
|
159
162
|
shouldRecallFocusedListEvidence
|
|
160
163
|
} from "./chunk-OH7QLI6W.js";
|
|
161
164
|
import {
|
|
162
165
|
ExtractionEngine
|
|
163
|
-
} from "./chunk-
|
|
166
|
+
} from "./chunk-AXIDQG5A.js";
|
|
164
167
|
import {
|
|
165
168
|
parseMemoryActionEligibilityContext
|
|
166
169
|
} from "./chunk-WFLBP5GC.js";
|
|
@@ -180,11 +183,14 @@ import {
|
|
|
180
183
|
judgeFactDurability,
|
|
181
184
|
validateProcedureExtraction
|
|
182
185
|
} from "./chunk-K2TDK7GG.js";
|
|
186
|
+
import {
|
|
187
|
+
buildExplicitCueRecallSection
|
|
188
|
+
} from "./chunk-TVIVY7KU.js";
|
|
183
189
|
import {
|
|
184
190
|
buildEntityRecallSection,
|
|
185
191
|
entityRecentTranscriptLookbackHours,
|
|
186
192
|
readRecentEntityTranscriptEntries
|
|
187
|
-
} from "./chunk-
|
|
193
|
+
} from "./chunk-CV6BBVYV.js";
|
|
188
194
|
import {
|
|
189
195
|
buildEventOrderRecallSection,
|
|
190
196
|
shouldRecallEventOrderEvidence
|
|
@@ -193,44 +199,41 @@ import {
|
|
|
193
199
|
pickFactEventTimeAnchor,
|
|
194
200
|
resolveFactEventTime
|
|
195
201
|
} from "./chunk-IAIPNEHD.js";
|
|
196
|
-
import {
|
|
197
|
-
buildExplicitCueRecallSection
|
|
198
|
-
} from "./chunk-TVIVY7KU.js";
|
|
199
202
|
import {
|
|
200
203
|
tryDirectAnswer
|
|
201
204
|
} from "./chunk-CSOYVTRX.js";
|
|
202
205
|
import {
|
|
203
206
|
EmbeddingFallback
|
|
204
207
|
} from "./chunk-YK6BDDHP.js";
|
|
208
|
+
import {
|
|
209
|
+
refreshConvergedNamespaces
|
|
210
|
+
} from "./chunk-W5XVQFLM.js";
|
|
205
211
|
import {
|
|
206
212
|
formatDaySummaryMemories
|
|
207
213
|
} from "./chunk-RPSYDM6C.js";
|
|
208
|
-
import {
|
|
209
|
-
refreshConvergedNamespaces
|
|
210
|
-
} from "./chunk-V5H6OJCR.js";
|
|
211
214
|
import {
|
|
212
215
|
builtInConnectorPackageSpecifier,
|
|
213
216
|
ensureBuiltInWearableConnectors,
|
|
214
217
|
getWearableConnector,
|
|
215
218
|
listWearableConnectors
|
|
216
|
-
} from "./chunk-
|
|
217
|
-
import {
|
|
218
|
-
RoutingRulesStore
|
|
219
|
-
} from "./chunk-XL24QQ63.js";
|
|
219
|
+
} from "./chunk-DCZBSE4F.js";
|
|
220
220
|
import {
|
|
221
221
|
normalizeReplaySessionKey
|
|
222
222
|
} from "./chunk-AJVLDJU6.js";
|
|
223
|
+
import {
|
|
224
|
+
RoutingRulesStore
|
|
225
|
+
} from "./chunk-XL24QQ63.js";
|
|
223
226
|
import {
|
|
224
227
|
compareVerifiedEpisodeResults,
|
|
225
228
|
searchVerifiedEpisodes
|
|
226
|
-
} from "./chunk-
|
|
229
|
+
} from "./chunk-FXTYIA46.js";
|
|
227
230
|
import {
|
|
228
231
|
ThreadingManager
|
|
229
232
|
} from "./chunk-OJP3N7UK.js";
|
|
230
233
|
import {
|
|
231
234
|
compareVerifiedSemanticRuleResults,
|
|
232
235
|
searchVerifiedSemanticRules
|
|
233
|
-
} from "./chunk-
|
|
236
|
+
} from "./chunk-QGR6OVGT.js";
|
|
234
237
|
import {
|
|
235
238
|
searchWorkProductLedgerEntries
|
|
236
239
|
} from "./chunk-WT6UL3UA.js";
|
|
@@ -243,18 +246,18 @@ import {
|
|
|
243
246
|
import {
|
|
244
247
|
runNamespaceMaintenanceFanout,
|
|
245
248
|
summarizeNamespaceMaintenanceHealth
|
|
246
|
-
} from "./chunk-
|
|
249
|
+
} from "./chunk-6MTSFX7A.js";
|
|
247
250
|
import {
|
|
248
251
|
NamespaceCatalog,
|
|
249
252
|
planNamespaceMaintenance
|
|
250
|
-
} from "./chunk-
|
|
253
|
+
} from "./chunk-4PC4PRJE.js";
|
|
254
|
+
import {
|
|
255
|
+
searchHarmonicRetrieval
|
|
256
|
+
} from "./chunk-AZ2QBGYB.js";
|
|
251
257
|
import {
|
|
252
258
|
isAboveImportanceThreshold,
|
|
253
259
|
scoreImportance
|
|
254
260
|
} from "./chunk-JXS5PDQ7.js";
|
|
255
|
-
import {
|
|
256
|
-
searchHarmonicRetrieval
|
|
257
|
-
} from "./chunk-QN7NTKRC.js";
|
|
258
261
|
import {
|
|
259
262
|
EXTRACTION_JUDGE_VERDICT_CATEGORY,
|
|
260
263
|
recordJudgeVerdict
|
|
@@ -262,14 +265,14 @@ import {
|
|
|
262
265
|
import {
|
|
263
266
|
recordEvalShadowRecall
|
|
264
267
|
} from "./chunk-MCA2X4WH.js";
|
|
265
|
-
import {
|
|
266
|
-
pruneOrphanCueAnchors
|
|
267
|
-
} from "./chunk-ACPCA4NO.js";
|
|
268
268
|
import {
|
|
269
269
|
collectNativeKnowledgeChunks,
|
|
270
270
|
formatNativeKnowledgeSection,
|
|
271
271
|
searchNativeKnowledge
|
|
272
272
|
} from "./chunk-2DQ2XREU.js";
|
|
273
|
+
import {
|
|
274
|
+
pruneOrphanCueAnchors
|
|
275
|
+
} from "./chunk-ACPCA4NO.js";
|
|
273
276
|
import {
|
|
274
277
|
applyCommitmentLedgerLifecycle
|
|
275
278
|
} from "./chunk-NOB2T2FC.js";
|
|
@@ -282,7 +285,10 @@ import {
|
|
|
282
285
|
materializeAfterSemanticConsolidation,
|
|
283
286
|
parseConsolidationResponse,
|
|
284
287
|
parseOperatorAwareConsolidationResponse
|
|
285
|
-
} from "./chunk-
|
|
288
|
+
} from "./chunk-VVG2BOKA.js";
|
|
289
|
+
import {
|
|
290
|
+
BootstrapEngine
|
|
291
|
+
} from "./chunk-MYVPLJOO.js";
|
|
286
292
|
import {
|
|
287
293
|
BoxBuilder
|
|
288
294
|
} from "./chunk-B7RWBZXW.js";
|
|
@@ -294,10 +300,13 @@ import {
|
|
|
294
300
|
} from "./chunk-UQ7RN5HK.js";
|
|
295
301
|
import {
|
|
296
302
|
SmartBuffer
|
|
297
|
-
} from "./chunk-
|
|
303
|
+
} from "./chunk-HLYR2TQL.js";
|
|
304
|
+
import {
|
|
305
|
+
isDisagreementPrompt
|
|
306
|
+
} from "./chunk-H3FZVNRN.js";
|
|
298
307
|
import {
|
|
299
308
|
detectMeetings
|
|
300
|
-
} from "./chunk-
|
|
309
|
+
} from "./chunk-O5FFBO2M.js";
|
|
301
310
|
import {
|
|
302
311
|
compileCorrectionRule,
|
|
303
312
|
correctionsFilePath,
|
|
@@ -320,15 +329,9 @@ import {
|
|
|
320
329
|
buildBehaviorSignalsForMemory,
|
|
321
330
|
dedupeBehaviorSignalsByMemoryAndHash
|
|
322
331
|
} from "./chunk-KD3QD3A5.js";
|
|
323
|
-
import {
|
|
324
|
-
BootstrapEngine
|
|
325
|
-
} from "./chunk-MYVPLJOO.js";
|
|
326
|
-
import {
|
|
327
|
-
isDisagreementPrompt
|
|
328
|
-
} from "./chunk-H3FZVNRN.js";
|
|
329
332
|
import {
|
|
330
333
|
MeetingsInputError
|
|
331
|
-
} from "./chunk-
|
|
334
|
+
} from "./chunk-XADV5IZ3.js";
|
|
332
335
|
import {
|
|
333
336
|
WearablesInputError,
|
|
334
337
|
describeErrorForOperator
|
|
@@ -349,7 +352,7 @@ import {
|
|
|
349
352
|
filterRecallCandidates,
|
|
350
353
|
isGenericRecallExcludedPath,
|
|
351
354
|
isTopLevelArchivePath
|
|
352
|
-
} from "./chunk-
|
|
355
|
+
} from "./chunk-J5LLX6IL.js";
|
|
353
356
|
import {
|
|
354
357
|
importCapsule
|
|
355
358
|
} from "./chunk-ZQOCRIGA.js";
|
|
@@ -367,9 +370,6 @@ import {
|
|
|
367
370
|
listTrustZoneRecords,
|
|
368
371
|
searchTrustZoneRecords
|
|
369
372
|
} from "./chunk-KQS72GCR.js";
|
|
370
|
-
import {
|
|
371
|
-
buildXraySnapshot
|
|
372
|
-
} from "./chunk-NSGU76YO.js";
|
|
373
373
|
import {
|
|
374
374
|
boundRecallContextComposition,
|
|
375
375
|
composeRecallContext,
|
|
@@ -377,6 +377,9 @@ import {
|
|
|
377
377
|
formatCuriosityFooter,
|
|
378
378
|
selectCuriosityQuestion
|
|
379
379
|
} from "./chunk-AHVEHR6K.js";
|
|
380
|
+
import {
|
|
381
|
+
buildXraySnapshot
|
|
382
|
+
} from "./chunk-QHFV6VNU.js";
|
|
380
383
|
import {
|
|
381
384
|
objectiveStateStoreOverrideForNamespace,
|
|
382
385
|
searchObjectiveStateSnapshots
|
|
@@ -393,34 +396,34 @@ import {
|
|
|
393
396
|
} from "./chunk-QDW3E4RD.js";
|
|
394
397
|
import {
|
|
395
398
|
shouldSkipImplicitExtraction
|
|
396
|
-
} from "./chunk-
|
|
399
|
+
} from "./chunk-37ZO6LLJ.js";
|
|
397
400
|
import {
|
|
398
401
|
NamespaceSearchRouter,
|
|
399
402
|
namespaceCollectionName
|
|
400
|
-
} from "./chunk-
|
|
403
|
+
} from "./chunk-VMMQDEN5.js";
|
|
401
404
|
import {
|
|
402
405
|
createConversationIndexRuntime,
|
|
403
406
|
createSearchBackend,
|
|
404
407
|
isSearchBackendEnabled
|
|
405
|
-
} from "./chunk-
|
|
408
|
+
} from "./chunk-AZM4CCAC.js";
|
|
406
409
|
import {
|
|
407
410
|
NoopSearchBackend
|
|
408
411
|
} from "./chunk-CYEPCZN5.js";
|
|
409
412
|
import {
|
|
410
413
|
NamespaceStorageRouter
|
|
411
|
-
} from "./chunk-
|
|
414
|
+
} from "./chunk-WQM326GS.js";
|
|
412
415
|
import {
|
|
413
416
|
writeConversationChunks
|
|
414
417
|
} from "./chunk-72A4L5JJ.js";
|
|
415
|
-
import {
|
|
416
|
-
GraphIndex
|
|
417
|
-
} from "./chunk-L2DPF4DF.js";
|
|
418
418
|
import {
|
|
419
419
|
searchCausalTrajectories
|
|
420
|
-
} from "./chunk-
|
|
420
|
+
} from "./chunk-AHZOMHWN.js";
|
|
421
|
+
import {
|
|
422
|
+
GraphIndex
|
|
423
|
+
} from "./chunk-BIJAWZYW.js";
|
|
421
424
|
import {
|
|
422
425
|
buildChainFollowupGenerator
|
|
423
|
-
} from "./chunk-
|
|
426
|
+
} from "./chunk-52UKFTUK.js";
|
|
424
427
|
import {
|
|
425
428
|
QmdResultResolver,
|
|
426
429
|
StorageManager,
|
|
@@ -439,10 +442,7 @@ import {
|
|
|
439
442
|
reconstructFusionInputs,
|
|
440
443
|
selfDeps,
|
|
441
444
|
serializeFusionDay
|
|
442
|
-
} from "./chunk-
|
|
443
|
-
import {
|
|
444
|
-
buildRetiredFactTombstoneInputs
|
|
445
|
-
} from "./chunk-ENTCVTQR.js";
|
|
445
|
+
} from "./chunk-VBHPOWBJ.js";
|
|
446
446
|
import {
|
|
447
447
|
bodyIsEscaped,
|
|
448
448
|
decodeTranscriptBody,
|
|
@@ -453,6 +453,9 @@ import {
|
|
|
453
453
|
saveSpeakerRegistry,
|
|
454
454
|
speakerRegistryKey
|
|
455
455
|
} from "./chunk-UHVXE24Y.js";
|
|
456
|
+
import {
|
|
457
|
+
buildRetiredFactTombstoneInputs
|
|
458
|
+
} from "./chunk-ENTCVTQR.js";
|
|
456
459
|
import {
|
|
457
460
|
canRecallToolScopedMemory,
|
|
458
461
|
shouldPromoteGlobalFactToShared,
|
|
@@ -465,7 +468,7 @@ import {
|
|
|
465
468
|
} from "./chunk-J6A3CX5N.js";
|
|
466
469
|
import {
|
|
467
470
|
confidenceTier
|
|
468
|
-
} from "./chunk-
|
|
471
|
+
} from "./chunk-UU3G6GUP.js";
|
|
469
472
|
import {
|
|
470
473
|
lintWorkspaceFiles,
|
|
471
474
|
rotateMarkdownFileToArchive
|
|
@@ -506,6 +509,7 @@ import {
|
|
|
506
509
|
} from "./chunk-M4A44LUA.js";
|
|
507
510
|
import {
|
|
508
511
|
applyTemporalSupersession,
|
|
512
|
+
lookupAttributeByNormalizedKey,
|
|
509
513
|
normalizeSupersessionKey,
|
|
510
514
|
propagateInvalidation,
|
|
511
515
|
shouldFilterSupersededFromRecall,
|
|
@@ -515,6 +519,11 @@ import {
|
|
|
515
519
|
isValidAsOf,
|
|
516
520
|
isValidityExpiredNow
|
|
517
521
|
} from "./chunk-6CIAGZ6X.js";
|
|
522
|
+
import {
|
|
523
|
+
FallbackLlmClient,
|
|
524
|
+
fallbackLlmRuntimeContextFromConfig,
|
|
525
|
+
gatewayTaskChainOptions
|
|
526
|
+
} from "./chunk-C23BYTJV.js";
|
|
518
527
|
import {
|
|
519
528
|
BulkImportBatchPartialFailureError,
|
|
520
529
|
COMPACTION_SIGNAL_MAX_AGE_MS,
|
|
@@ -554,7 +563,7 @@ import {
|
|
|
554
563
|
throwIfRecallAborted,
|
|
555
564
|
tokenizeRecallQuery,
|
|
556
565
|
utcDateKeysForLocalDay
|
|
557
|
-
} from "./chunk-
|
|
566
|
+
} from "./chunk-ZMYDYNI4.js";
|
|
558
567
|
import {
|
|
559
568
|
inferIntentFromText,
|
|
560
569
|
intentCompatibilityScore,
|
|
@@ -566,17 +575,15 @@ import {
|
|
|
566
575
|
getCachedQmdRecall,
|
|
567
576
|
setCachedQmdRecall
|
|
568
577
|
} from "./chunk-42JKGUFJ.js";
|
|
569
|
-
import {
|
|
570
|
-
FallbackLlmClient,
|
|
571
|
-
fallbackLlmRuntimeContextFromConfig,
|
|
572
|
-
gatewayTaskChainOptions
|
|
573
|
-
} from "./chunk-C23BYTJV.js";
|
|
574
578
|
import {
|
|
575
579
|
assertExternalWikiRootOutsideMemoryDirCanonical
|
|
576
580
|
} from "./chunk-JV3C2MNQ.js";
|
|
577
581
|
import {
|
|
578
582
|
sanitizeMemoryContent
|
|
579
583
|
} from "./chunk-5GKPFL3S.js";
|
|
584
|
+
import {
|
|
585
|
+
coerceBool
|
|
586
|
+
} from "./chunk-PQVCH2AE.js";
|
|
580
587
|
import {
|
|
581
588
|
MEMORY_ID_PATTERN,
|
|
582
589
|
parseIdOrHandle,
|
|
@@ -616,7 +623,8 @@ import {
|
|
|
616
623
|
} from "./chunk-GCASGYIO.js";
|
|
617
624
|
import {
|
|
618
625
|
inferMemoryStatus,
|
|
619
|
-
isActiveMemoryStatus
|
|
626
|
+
isActiveMemoryStatus,
|
|
627
|
+
toMemoryPathRel
|
|
620
628
|
} from "./chunk-7RJUVTVF.js";
|
|
621
629
|
import {
|
|
622
630
|
ContentHashIndex
|
|
@@ -678,6 +686,9 @@ import {
|
|
|
678
686
|
import {
|
|
679
687
|
SecureStoreLockedError
|
|
680
688
|
} from "./chunk-XQ3HXAQH.js";
|
|
689
|
+
import {
|
|
690
|
+
isErrnoCode
|
|
691
|
+
} from "./chunk-5UZXUTVO.js";
|
|
681
692
|
import {
|
|
682
693
|
ALL_CATEGORY_DIRS,
|
|
683
694
|
ALL_CATEGORY_KEYS,
|
|
@@ -689,7 +700,7 @@ import {
|
|
|
689
700
|
} from "./chunk-3WCASNQZ.js";
|
|
690
701
|
|
|
691
702
|
// src/orchestrator.ts
|
|
692
|
-
import
|
|
703
|
+
import path19 from "path";
|
|
693
704
|
import { createHash as createHash6 } from "crypto";
|
|
694
705
|
|
|
695
706
|
// src/orchestration/tier-migration-coordinator.ts
|
|
@@ -2184,7 +2195,7 @@ var RecallRerankCoordinator = class _RecallRerankCoordinator {
|
|
|
2184
2195
|
namespaces,
|
|
2185
2196
|
{
|
|
2186
2197
|
readNamespaceMemories: async (ns) => (await this.getStorage(ns)).readAllMemories(),
|
|
2187
|
-
readMemoryFrontmatter: async (
|
|
2198
|
+
readMemoryFrontmatter: async (path34, preferredNamespace) => {
|
|
2188
2199
|
if (!fallbackReader) {
|
|
2189
2200
|
for (const ns of namespaces) {
|
|
2190
2201
|
try {
|
|
@@ -2196,7 +2207,7 @@ var RecallRerankCoordinator = class _RecallRerankCoordinator {
|
|
|
2196
2207
|
}
|
|
2197
2208
|
if (!fallbackReader) return null;
|
|
2198
2209
|
const memory = await this.readQmdResultMemory(
|
|
2199
|
-
|
|
2210
|
+
path34,
|
|
2200
2211
|
fallbackReader,
|
|
2201
2212
|
namespaces,
|
|
2202
2213
|
preferredNamespace
|
|
@@ -2701,6 +2712,113 @@ ${chunk.content}` : chunk.content;
|
|
|
2701
2712
|
}
|
|
2702
2713
|
};
|
|
2703
2714
|
|
|
2715
|
+
// src/orchestration/update-localization.ts
|
|
2716
|
+
function mergeMemorySnapshots(hot, cold, storageDir) {
|
|
2717
|
+
const merged = [];
|
|
2718
|
+
const indexById = /* @__PURE__ */ new Map();
|
|
2719
|
+
for (const memory of [...hot, ...cold]) {
|
|
2720
|
+
const id = memory.frontmatter.id;
|
|
2721
|
+
const existingIndex = indexById.get(id);
|
|
2722
|
+
if (existingIndex === void 0) {
|
|
2723
|
+
indexById.set(id, merged.length);
|
|
2724
|
+
merged.push(memory);
|
|
2725
|
+
continue;
|
|
2726
|
+
}
|
|
2727
|
+
const existing = merged[existingIndex];
|
|
2728
|
+
if (!isActiveMemoryStatus(inferLocalizationMemoryStatus(existing, storageDir)) && isActiveMemoryStatus(inferLocalizationMemoryStatus(memory, storageDir))) {
|
|
2729
|
+
merged[existingIndex] = memory;
|
|
2730
|
+
}
|
|
2731
|
+
}
|
|
2732
|
+
return merged;
|
|
2733
|
+
}
|
|
2734
|
+
function cap(value) {
|
|
2735
|
+
return Number.isFinite(value) ? Math.max(0, Math.floor(value)) : 0;
|
|
2736
|
+
}
|
|
2737
|
+
function normalizeEntityRef(value) {
|
|
2738
|
+
if (typeof value !== "string") return void 0;
|
|
2739
|
+
const normalized = normalizeSupersessionKey(value);
|
|
2740
|
+
return normalized.length > 0 ? normalized : void 0;
|
|
2741
|
+
}
|
|
2742
|
+
function compareCandidates(left, right) {
|
|
2743
|
+
const leftScore = Number.isFinite(left.score) ? left.score : Number.NEGATIVE_INFINITY;
|
|
2744
|
+
const rightScore = Number.isFinite(right.score) ? right.score : Number.NEGATIVE_INFINITY;
|
|
2745
|
+
if (leftScore !== rightScore) return leftScore > rightScore ? -1 : 1;
|
|
2746
|
+
return left.id < right.id ? -1 : left.id > right.id ? 1 : 0;
|
|
2747
|
+
}
|
|
2748
|
+
function anchorScore(memory, anchor) {
|
|
2749
|
+
const attributes = anchor.attributes;
|
|
2750
|
+
if (attributes && Object.keys(attributes).length > 0) {
|
|
2751
|
+
const candidateAttributes = memory.frontmatter.structuredAttributes;
|
|
2752
|
+
if (!candidateAttributes) return 0;
|
|
2753
|
+
let overlap = 0;
|
|
2754
|
+
for (const key of Object.keys(attributes)) {
|
|
2755
|
+
if (lookupAttributeByNormalizedKey(candidateAttributes, key) !== void 0) overlap++;
|
|
2756
|
+
}
|
|
2757
|
+
return overlap;
|
|
2758
|
+
}
|
|
2759
|
+
const created = Date.parse(memory.frontmatter.created);
|
|
2760
|
+
return Number.isFinite(created) ? created : 0;
|
|
2761
|
+
}
|
|
2762
|
+
function toAnchorCandidate(memory, anchor) {
|
|
2763
|
+
return {
|
|
2764
|
+
id: memory.frontmatter.id,
|
|
2765
|
+
content: memory.content,
|
|
2766
|
+
category: memory.frontmatter.category,
|
|
2767
|
+
source: "anchor",
|
|
2768
|
+
score: anchorScore(memory, anchor)
|
|
2769
|
+
};
|
|
2770
|
+
}
|
|
2771
|
+
function inferLocalizationMemoryStatus(memory, storageDir) {
|
|
2772
|
+
const pathRel = storageDir ? toMemoryPathRel(storageDir, memory.path) : memory.path;
|
|
2773
|
+
return inferMemoryStatus(memory.frontmatter, pathRel);
|
|
2774
|
+
}
|
|
2775
|
+
async function localizeUpdateCandidates(deps, anchor, newContent, options) {
|
|
2776
|
+
const maxCandidates = cap(options.maxCandidates);
|
|
2777
|
+
if (maxCandidates === 0) return [];
|
|
2778
|
+
const anchorLimit = cap(options.anchorCandidates);
|
|
2779
|
+
const searchLimit = cap(options.searchCandidates);
|
|
2780
|
+
const anchorCandidates = [];
|
|
2781
|
+
const normalizedAnchorEntityRef = normalizeEntityRef(anchor.entityRef);
|
|
2782
|
+
if (normalizedAnchorEntityRef !== void 0 && anchorLimit > 0) {
|
|
2783
|
+
const hot = await deps.storage.readAllMemories();
|
|
2784
|
+
const cold = deps.storage.readAllColdMemories ? await deps.storage.readAllColdMemories() : [];
|
|
2785
|
+
const memories = mergeMemorySnapshots(hot, cold, deps.storage.dir);
|
|
2786
|
+
for (const memory of memories) {
|
|
2787
|
+
if (inferLocalizationMemoryStatus(memory, deps.storage.dir) !== "active") continue;
|
|
2788
|
+
const normalizedCandidateEntityRef = normalizeEntityRef(memory.frontmatter.entityRef);
|
|
2789
|
+
if (normalizedCandidateEntityRef !== normalizedAnchorEntityRef) continue;
|
|
2790
|
+
if (memory.frontmatter.category !== anchor.category) continue;
|
|
2791
|
+
anchorCandidates.push(toAnchorCandidate(memory, anchor));
|
|
2792
|
+
}
|
|
2793
|
+
anchorCandidates.sort(compareCandidates);
|
|
2794
|
+
anchorCandidates.splice(anchorLimit);
|
|
2795
|
+
}
|
|
2796
|
+
const searchCandidates = [];
|
|
2797
|
+
if (searchLimit > 0) {
|
|
2798
|
+
const searchHits = await deps.qmdSearch(newContent, searchLimit);
|
|
2799
|
+
for (const hit of searchHits) {
|
|
2800
|
+
searchCandidates.push({
|
|
2801
|
+
id: hit.id,
|
|
2802
|
+
content: hit.content,
|
|
2803
|
+
category: hit.category,
|
|
2804
|
+
source: "search",
|
|
2805
|
+
score: hit.score
|
|
2806
|
+
});
|
|
2807
|
+
}
|
|
2808
|
+
searchCandidates.sort(compareCandidates);
|
|
2809
|
+
searchCandidates.splice(searchLimit);
|
|
2810
|
+
}
|
|
2811
|
+
const merged = [];
|
|
2812
|
+
const seen = /* @__PURE__ */ new Set();
|
|
2813
|
+
for (const candidate of [...anchorCandidates, ...searchCandidates]) {
|
|
2814
|
+
if (seen.has(candidate.id)) continue;
|
|
2815
|
+
seen.add(candidate.id);
|
|
2816
|
+
merged.push(candidate);
|
|
2817
|
+
if (merged.length >= maxCandidates) break;
|
|
2818
|
+
}
|
|
2819
|
+
return merged;
|
|
2820
|
+
}
|
|
2821
|
+
|
|
2704
2822
|
// src/orchestration/contradiction-linking-coordinator.ts
|
|
2705
2823
|
var ContradictionLinkingCoordinator = class {
|
|
2706
2824
|
getConfig;
|
|
@@ -2723,31 +2841,125 @@ var ContradictionLinkingCoordinator = class {
|
|
|
2723
2841
|
* Check if a new memory contradicts an existing one.
|
|
2724
2842
|
* Uses QMD to find similar memories, then LLM to verify contradiction.
|
|
2725
2843
|
*/
|
|
2726
|
-
async checkForContradiction(content, category, namespaceScope) {
|
|
2727
|
-
if (!this.isSearchAvailable()) return null;
|
|
2844
|
+
async checkForContradiction(content, category, namespaceScope, anchor) {
|
|
2728
2845
|
const config = this.getConfig();
|
|
2729
|
-
const
|
|
2730
|
-
|
|
2731
|
-
|
|
2732
|
-
|
|
2733
|
-
|
|
2734
|
-
|
|
2735
|
-
|
|
2736
|
-
|
|
2737
|
-
|
|
2738
|
-
}
|
|
2739
|
-
const
|
|
2740
|
-
|
|
2741
|
-
|
|
2742
|
-
|
|
2743
|
-
|
|
2744
|
-
|
|
2745
|
-
|
|
2746
|
-
|
|
2747
|
-
continue;
|
|
2846
|
+
const localization = config.contradictionLocalization;
|
|
2847
|
+
const anchorEnabled = coerceBool(localization?.anchorEnabled) ?? true;
|
|
2848
|
+
if (!anchorEnabled) {
|
|
2849
|
+
if (!this.isSearchAvailable()) return null;
|
|
2850
|
+
const results = await this.searchAcrossNamespaces({
|
|
2851
|
+
query: content,
|
|
2852
|
+
namespaces: [namespaceScope],
|
|
2853
|
+
maxResults: 5,
|
|
2854
|
+
mode: "search"
|
|
2855
|
+
});
|
|
2856
|
+
for (const result of results) {
|
|
2857
|
+
if (result.score < config.contradictionSimilarityThreshold) continue;
|
|
2858
|
+
const memoryId = this.extractMemoryIdsFromResults([result])[0];
|
|
2859
|
+
if (!memoryId) continue;
|
|
2860
|
+
const resultNamespace = this.namespaceFromPath(result.path);
|
|
2861
|
+
if (resultNamespace !== namespaceScope) continue;
|
|
2862
|
+
const resultStorage2 = await this.storageForNamespace(resultNamespace);
|
|
2863
|
+
const existingMemory = await resultStorage2.getMemoryById(memoryId);
|
|
2864
|
+
if (!existingMemory) continue;
|
|
2865
|
+
if (inferLocalizationMemoryStatus(existingMemory, resultStorage2.dir) !== "active") continue;
|
|
2866
|
+
const verification = await this.getExtraction().verifyContradiction(
|
|
2867
|
+
{ content, category },
|
|
2868
|
+
{
|
|
2869
|
+
id: existingMemory.frontmatter.id,
|
|
2870
|
+
content: existingMemory.content,
|
|
2871
|
+
category: existingMemory.frontmatter.category,
|
|
2872
|
+
created: existingMemory.frontmatter.created
|
|
2873
|
+
}
|
|
2874
|
+
);
|
|
2875
|
+
if (!verification) continue;
|
|
2876
|
+
if (verification.isContradiction && verification.confidence >= config.contradictionMinConfidence) {
|
|
2877
|
+
if (verification.whichIsNewer === "first") {
|
|
2878
|
+
log.info(
|
|
2879
|
+
`detected contradiction (confidence: ${verification.confidence}): ${existingMemory.frontmatter.id} vs new memory \u2014 existing is newer, incoming fact is stale`
|
|
2880
|
+
);
|
|
2881
|
+
continue;
|
|
2882
|
+
}
|
|
2883
|
+
log.info(
|
|
2884
|
+
`detected contradiction (confidence: ${verification.confidence}): ${existingMemory.frontmatter.id} vs new memory${config.contradictionAutoResolve ? " (auto-resolved)" : " (queued for manual review)"}`
|
|
2885
|
+
);
|
|
2886
|
+
return {
|
|
2887
|
+
supersededId: existingMemory.frontmatter.id,
|
|
2888
|
+
confidence: verification.confidence,
|
|
2889
|
+
reason: verification.reasoning,
|
|
2890
|
+
supersededPath: existingMemory.path,
|
|
2891
|
+
supersededCreated: existingMemory.frontmatter.created,
|
|
2892
|
+
supersededTags: existingMemory.frontmatter.tags ?? []
|
|
2893
|
+
};
|
|
2894
|
+
}
|
|
2748
2895
|
}
|
|
2749
|
-
|
|
2750
|
-
|
|
2896
|
+
return null;
|
|
2897
|
+
}
|
|
2898
|
+
const localizationOptions = localization ?? {
|
|
2899
|
+
anchorEnabled: true,
|
|
2900
|
+
anchorCandidates: 5,
|
|
2901
|
+
searchCandidates: 5,
|
|
2902
|
+
maxCandidates: 8
|
|
2903
|
+
};
|
|
2904
|
+
const resultStorage = await this.storageForNamespace(namespaceScope);
|
|
2905
|
+
let anchorSnapshot = anchor?.storageSnapshot;
|
|
2906
|
+
const anchorLimit = localizationOptions.anchorCandidates;
|
|
2907
|
+
if (!anchorSnapshot && Number.isInteger(anchorLimit) && anchorLimit > 0 && typeof anchor?.entityRef === "string" && anchor?.entityRef.trim().length > 0) {
|
|
2908
|
+
const [hot, cold] = await Promise.all([
|
|
2909
|
+
resultStorage.readAllMemories(),
|
|
2910
|
+
typeof resultStorage.readAllColdMemories === "function" ? resultStorage.readAllColdMemories() : Promise.resolve([])
|
|
2911
|
+
]);
|
|
2912
|
+
anchorSnapshot = mergeMemorySnapshots(hot, cold, resultStorage.dir);
|
|
2913
|
+
}
|
|
2914
|
+
const anchorMemoryById = anchorSnapshot ? new Map(anchorSnapshot.map((memory) => [memory.frontmatter.id, memory])) : void 0;
|
|
2915
|
+
const candidates = await localizeUpdateCandidates(
|
|
2916
|
+
{
|
|
2917
|
+
storage: anchorSnapshot ? {
|
|
2918
|
+
dir: resultStorage.dir,
|
|
2919
|
+
readAllMemories: async () => anchorSnapshot ?? [],
|
|
2920
|
+
readAllColdMemories: async () => []
|
|
2921
|
+
} : resultStorage,
|
|
2922
|
+
qmdSearch: async (query, limit) => {
|
|
2923
|
+
if (!this.isSearchAvailable()) {
|
|
2924
|
+
log.warn("[contradiction-linking] QMD unavailable; continuing with anchor candidates");
|
|
2925
|
+
return [];
|
|
2926
|
+
}
|
|
2927
|
+
const results = await this.searchAcrossNamespaces({
|
|
2928
|
+
query,
|
|
2929
|
+
namespaces: [namespaceScope],
|
|
2930
|
+
maxResults: limit,
|
|
2931
|
+
mode: "search"
|
|
2932
|
+
});
|
|
2933
|
+
const hits = [];
|
|
2934
|
+
for (const result of results) {
|
|
2935
|
+
if (result.score < config.contradictionSimilarityThreshold) continue;
|
|
2936
|
+
const memoryId = this.extractMemoryIdsFromResults([result])[0];
|
|
2937
|
+
if (!memoryId) continue;
|
|
2938
|
+
if (this.namespaceFromPath(result.path) !== namespaceScope) continue;
|
|
2939
|
+
const existingMemory = anchorMemoryById?.get(memoryId) ?? await resultStorage.getMemoryById(memoryId);
|
|
2940
|
+
if (!existingMemory || inferLocalizationMemoryStatus(existingMemory, resultStorage.dir) !== "active") continue;
|
|
2941
|
+
hits.push({
|
|
2942
|
+
id: memoryId,
|
|
2943
|
+
content: existingMemory.content,
|
|
2944
|
+
category: existingMemory.frontmatter.category,
|
|
2945
|
+
score: result.score
|
|
2946
|
+
});
|
|
2947
|
+
}
|
|
2948
|
+
return hits;
|
|
2949
|
+
}
|
|
2950
|
+
},
|
|
2951
|
+
{
|
|
2952
|
+
entityRef: anchor?.entityRef,
|
|
2953
|
+
category,
|
|
2954
|
+
attributes: anchor?.structuredAttributes ?? anchor?.attributes
|
|
2955
|
+
},
|
|
2956
|
+
content,
|
|
2957
|
+
localizationOptions
|
|
2958
|
+
);
|
|
2959
|
+
for (const candidate of candidates) {
|
|
2960
|
+
const existingMemory = anchorMemoryById?.get(candidate.id) ?? await resultStorage.getMemoryById(candidate.id);
|
|
2961
|
+
if (!existingMemory || inferLocalizationMemoryStatus(existingMemory, resultStorage.dir) !== "active") continue;
|
|
2962
|
+
const verification = await this.getExtraction().verifyContradiction(
|
|
2751
2963
|
{ content, category },
|
|
2752
2964
|
{
|
|
2753
2965
|
id: existingMemory.frontmatter.id,
|
|
@@ -2802,13 +3014,23 @@ var ContradictionLinkingCoordinator = class {
|
|
|
2802
3014
|
}
|
|
2803
3015
|
}
|
|
2804
3016
|
if (!contradiction || !config.contradictionAutoResolve || postWriteGuard) {
|
|
2805
|
-
return;
|
|
3017
|
+
return postWriteGuard ? "blocked" : "not_attempted";
|
|
2806
3018
|
}
|
|
2807
3019
|
let oldMemory = null;
|
|
2808
|
-
|
|
2809
|
-
|
|
2810
|
-
|
|
2811
|
-
|
|
3020
|
+
if (coerceBool(config.dependencyPropagation?.enabled) === true) {
|
|
3021
|
+
try {
|
|
3022
|
+
const [hot, cold] = await Promise.all([
|
|
3023
|
+
typeof storage.readAllMemories === "function" ? storage.readAllMemories() : storage.getMemoryById(contradiction.supersededId).then(
|
|
3024
|
+
(memory) => memory ? [memory] : []
|
|
3025
|
+
),
|
|
3026
|
+
typeof storage.readAllColdMemories === "function" ? storage.readAllColdMemories() : Promise.resolve([])
|
|
3027
|
+
]);
|
|
3028
|
+
oldMemory = mergeMemorySnapshots(hot, cold, storage.dir).find(
|
|
3029
|
+
(memory) => memory.frontmatter.id === contradiction.supersededId
|
|
3030
|
+
) ?? null;
|
|
3031
|
+
} catch (err) {
|
|
3032
|
+
log.warn(`contradiction propagation snapshot failed for ${contradiction.supersededId}: ${err}`);
|
|
3033
|
+
}
|
|
2812
3034
|
}
|
|
2813
3035
|
try {
|
|
2814
3036
|
const superseded = await storage.supersedeMemory(
|
|
@@ -2816,7 +3038,48 @@ var ContradictionLinkingCoordinator = class {
|
|
|
2816
3038
|
newMemoryId,
|
|
2817
3039
|
contradiction.reason
|
|
2818
3040
|
);
|
|
2819
|
-
if (!superseded)
|
|
3041
|
+
if (!superseded) {
|
|
3042
|
+
let mergedSnapshot;
|
|
3043
|
+
try {
|
|
3044
|
+
const [hot, cold] = await Promise.all([
|
|
3045
|
+
typeof storage.readAllMemories === "function" ? storage.readAllMemories() : Promise.all([
|
|
3046
|
+
storage.getMemoryById(contradiction.supersededId),
|
|
3047
|
+
storage.getMemoryById(newMemoryId)
|
|
3048
|
+
]).then(
|
|
3049
|
+
(memories) => memories.filter((memory) => memory !== null)
|
|
3050
|
+
),
|
|
3051
|
+
typeof storage.readAllColdMemories === "function" ? storage.readAllColdMemories() : Promise.resolve([])
|
|
3052
|
+
]);
|
|
3053
|
+
mergedSnapshot = mergeMemorySnapshots(hot, cold, storage.dir);
|
|
3054
|
+
} catch (err) {
|
|
3055
|
+
log.warn(
|
|
3056
|
+
`contradiction auto-resolve race check failed for ${contradiction.supersededId}: ${err}`
|
|
3057
|
+
);
|
|
3058
|
+
return "supersede_failed";
|
|
3059
|
+
}
|
|
3060
|
+
const target = mergedSnapshot.find(
|
|
3061
|
+
(memory) => memory.frontmatter.id === contradiction.supersededId
|
|
3062
|
+
);
|
|
3063
|
+
if (!target) return "supersede_failed";
|
|
3064
|
+
const losingMemory = mergedSnapshot.find(
|
|
3065
|
+
(memory) => memory.frontmatter.id === newMemoryId && inferLocalizationMemoryStatus(memory, storage.dir) === "active"
|
|
3066
|
+
);
|
|
3067
|
+
if (!losingMemory) return "supersede_failed";
|
|
3068
|
+
try {
|
|
3069
|
+
if (losingMemory.frontmatter.supersedes === contradiction.supersededId) {
|
|
3070
|
+
const cleared = await storage.writeMemoryFrontmatter(losingMemory, {
|
|
3071
|
+
supersedes: void 0
|
|
3072
|
+
});
|
|
3073
|
+
if (cleared === false) return "supersedes_clear_failed";
|
|
3074
|
+
}
|
|
3075
|
+
} catch (err) {
|
|
3076
|
+
log.warn(
|
|
3077
|
+
`contradiction auto-resolve losing supersedes clear failed for ${newMemoryId}: ${err}`
|
|
3078
|
+
);
|
|
3079
|
+
return "supersedes_clear_failed";
|
|
3080
|
+
}
|
|
3081
|
+
return inferLocalizationMemoryStatus(target, storage.dir) === "active" ? "supersede_failed" : "lost_race";
|
|
3082
|
+
}
|
|
2820
3083
|
if (oldMemory) {
|
|
2821
3084
|
try {
|
|
2822
3085
|
await propagateInvalidation(
|
|
@@ -2838,17 +3101,25 @@ var ContradictionLinkingCoordinator = class {
|
|
|
2838
3101
|
}
|
|
2839
3102
|
}
|
|
2840
3103
|
if (resolveIndexingCapabilities(config).queryAwareIndexing && contradiction.supersededPath) {
|
|
2841
|
-
|
|
2842
|
-
|
|
2843
|
-
|
|
2844
|
-
|
|
2845
|
-
|
|
2846
|
-
|
|
3104
|
+
try {
|
|
3105
|
+
await deindexMemoryAsync(
|
|
3106
|
+
config.memoryDir,
|
|
3107
|
+
contradiction.supersededPath,
|
|
3108
|
+
contradiction.supersededCreated,
|
|
3109
|
+
contradiction.supersededTags
|
|
3110
|
+
);
|
|
3111
|
+
} catch (err) {
|
|
3112
|
+
log.warn(
|
|
3113
|
+
`contradiction auto-resolve deindex failed for ${contradiction.supersededId}: ${err}`
|
|
3114
|
+
);
|
|
3115
|
+
}
|
|
2847
3116
|
}
|
|
3117
|
+
return "resolved";
|
|
2848
3118
|
} catch (err) {
|
|
2849
3119
|
log.warn(
|
|
2850
3120
|
`contradiction auto-resolve supersede failed for ${contradiction.supersededId}: ${err}`
|
|
2851
3121
|
);
|
|
3122
|
+
return "supersede_failed";
|
|
2852
3123
|
}
|
|
2853
3124
|
}
|
|
2854
3125
|
// ---------------------------------------------------------------------------
|
|
@@ -3690,6 +3961,64 @@ async function persistConstructedHarmonicRecords(options) {
|
|
|
3690
3961
|
}
|
|
3691
3962
|
}
|
|
3692
3963
|
|
|
3964
|
+
// src/orchestration/extraction-anchor-snapshot.ts
|
|
3965
|
+
import path5 from "path";
|
|
3966
|
+
var ExtractionAnchorSnapshot = class {
|
|
3967
|
+
constructor(options = {}) {
|
|
3968
|
+
this.options = options;
|
|
3969
|
+
}
|
|
3970
|
+
options;
|
|
3971
|
+
snapshots = /* @__PURE__ */ new WeakMap();
|
|
3972
|
+
refreshFailed = /* @__PURE__ */ new WeakSet();
|
|
3973
|
+
failOpenRead(storage, snapshot) {
|
|
3974
|
+
return snapshot.catch((error) => {
|
|
3975
|
+
this.refreshFailed.add(storage);
|
|
3976
|
+
if (this.snapshots.get(storage) === snapshot) this.snapshots.delete(storage);
|
|
3977
|
+
this.options.onRefreshError?.(error);
|
|
3978
|
+
return [];
|
|
3979
|
+
});
|
|
3980
|
+
}
|
|
3981
|
+
get(storage, entityRef) {
|
|
3982
|
+
const candidateLimit = this.options.candidateLimit ?? 5;
|
|
3983
|
+
if (this.options.enabled === false || !Number.isInteger(candidateLimit) || candidateLimit <= 0 || typeof entityRef !== "string" || entityRef.trim().length === 0) {
|
|
3984
|
+
return Promise.resolve(void 0);
|
|
3985
|
+
}
|
|
3986
|
+
if (this.refreshFailed.has(storage)) return Promise.resolve([]);
|
|
3987
|
+
const cached = this.snapshots.get(storage);
|
|
3988
|
+
if (cached) return this.failOpenRead(storage, cached);
|
|
3989
|
+
const snapshot = Promise.all([
|
|
3990
|
+
storage.readAllMemories(),
|
|
3991
|
+
storage.readAllColdMemories()
|
|
3992
|
+
]).then(([hot, cold]) => mergeMemorySnapshots(hot, cold, storage.dir));
|
|
3993
|
+
this.snapshots.set(storage, snapshot);
|
|
3994
|
+
return this.failOpenRead(storage, snapshot);
|
|
3995
|
+
}
|
|
3996
|
+
async replace(storage, memoryId, category, pathById) {
|
|
3997
|
+
if (this.refreshFailed.has(storage)) return;
|
|
3998
|
+
try {
|
|
3999
|
+
const cached = this.snapshots.get(storage);
|
|
4000
|
+
if (!cached) return;
|
|
4001
|
+
const snapshot = await cached;
|
|
4002
|
+
const relativePath = resolvePersistedMemoryRelativePath({ memoryId, pathById, category });
|
|
4003
|
+
const memory = await storage.readMemoryByPath(path5.join(storage.dir, relativePath));
|
|
4004
|
+
if (!memory) return;
|
|
4005
|
+
const existingIndex = snapshot.findIndex((entry) => entry.frontmatter.id === memoryId);
|
|
4006
|
+
if (existingIndex >= 0) snapshot.splice(existingIndex, 1);
|
|
4007
|
+
snapshot.push(memory);
|
|
4008
|
+
} catch (error) {
|
|
4009
|
+
this.refreshFailed.add(storage);
|
|
4010
|
+
this.options.onRefreshError?.(error);
|
|
4011
|
+
}
|
|
4012
|
+
}
|
|
4013
|
+
async remove(storage, memoryId) {
|
|
4014
|
+
const cached = this.snapshots.get(storage);
|
|
4015
|
+
if (!cached) return;
|
|
4016
|
+
const snapshot = await cached;
|
|
4017
|
+
const index = snapshot.findIndex((entry) => entry.frontmatter.id === memoryId);
|
|
4018
|
+
if (index >= 0) snapshot.splice(index, 1);
|
|
4019
|
+
}
|
|
4020
|
+
};
|
|
4021
|
+
|
|
3693
4022
|
// src/orchestration/extraction-persist.ts
|
|
3694
4023
|
var ExtractionPersistCoordinator = class {
|
|
3695
4024
|
constructor(deps) {
|
|
@@ -3729,6 +4058,11 @@ var ExtractionPersistCoordinator = class {
|
|
|
3729
4058
|
};
|
|
3730
4059
|
const persistedIds = [];
|
|
3731
4060
|
const memoryPathById = /* @__PURE__ */ new Map();
|
|
4061
|
+
const anchorSnapshots = new ExtractionAnchorSnapshot({
|
|
4062
|
+
enabled: coerceBool(this.deps.config.contradictionLocalization?.anchorEnabled) ?? true,
|
|
4063
|
+
candidateLimit: this.deps.config.contradictionLocalization?.anchorCandidates,
|
|
4064
|
+
onRefreshError: (error) => log.warn(`anchor snapshot update failed; using empty snapshot: ${error}`)
|
|
4065
|
+
});
|
|
3732
4066
|
const supersessionOrderingAt = (validAt) => validAt && validAt.length > 0 ? validAt : (/* @__PURE__ */ new Date()).toISOString();
|
|
3733
4067
|
const pendingReviewPersistedIds = [];
|
|
3734
4068
|
const persistedIdsByStorage = /* @__PURE__ */ new Map();
|
|
@@ -4753,12 +5087,19 @@ var ExtractionPersistCoordinator = class {
|
|
|
4753
5087
|
let links = [];
|
|
4754
5088
|
let contradictionDetected = false;
|
|
4755
5089
|
let contradiction;
|
|
4756
|
-
if (resolveRecallEnhancementCapabilities(this.deps.config).contradictionDetection &&
|
|
5090
|
+
if (resolveRecallEnhancementCapabilities(this.deps.config).contradictionDetection && faithfulnessEnforceStatus !== "pending_review") {
|
|
4757
5091
|
const targetNamespace = this.deps.storageDirNamespace(targetStorage.dir);
|
|
5092
|
+
const candidateEntityRef = fact.entityRef;
|
|
5093
|
+
const factEntityRef = typeof candidateEntityRef === "string" ? candidateEntityRef : void 0;
|
|
4758
5094
|
contradiction = await this.deps.checkForContradiction(
|
|
4759
5095
|
fact.content,
|
|
4760
5096
|
writeCategory,
|
|
4761
|
-
targetNamespace
|
|
5097
|
+
targetNamespace,
|
|
5098
|
+
{
|
|
5099
|
+
entityRef: factEntityRef,
|
|
5100
|
+
structuredAttributes: fact.structuredAttributes,
|
|
5101
|
+
storageSnapshot: await anchorSnapshots.get(targetStorage, factEntityRef)
|
|
5102
|
+
}
|
|
4762
5103
|
);
|
|
4763
5104
|
if (contradiction) {
|
|
4764
5105
|
contradictionDetected = true;
|
|
@@ -4847,12 +5188,15 @@ var ExtractionPersistCoordinator = class {
|
|
|
4847
5188
|
const parentId = parentWrite.id;
|
|
4848
5189
|
const tombstoneBlocked2 = parentWrite.tombstoneBlocked;
|
|
4849
5190
|
const postWriteGuard2 = faithfulnessEnforceStatus === "pending_review" || tombstoneBlocked2;
|
|
4850
|
-
await this.deps.applyDeferredContradictionResolve(
|
|
5191
|
+
const contradictionOutcome = await this.deps.applyDeferredContradictionResolve(
|
|
4851
5192
|
contradiction,
|
|
4852
5193
|
targetStorage,
|
|
4853
5194
|
parentId,
|
|
4854
5195
|
postWriteGuard2
|
|
4855
5196
|
);
|
|
5197
|
+
if (contradictionOutcome === "resolved" || contradictionOutcome === "lost_race") {
|
|
5198
|
+
await anchorSnapshots.remove(targetStorage, contradiction.supersededId);
|
|
5199
|
+
}
|
|
4856
5200
|
try {
|
|
4857
5201
|
const chunkTags = parentWriteEnvelope.tags.filter((tag) => tag !== "chunked");
|
|
4858
5202
|
for (const chunk of chunkResult.chunks) {
|
|
@@ -4922,6 +5266,7 @@ var ExtractionPersistCoordinator = class {
|
|
|
4922
5266
|
category: writeCategory,
|
|
4923
5267
|
harmonicFact
|
|
4924
5268
|
});
|
|
5269
|
+
await anchorSnapshots.replace(targetStorage, parentId, writeCategory, memoryPathById);
|
|
4925
5270
|
if (!postWriteGuard2 && threadEpisodeIdsForGraph && !threadEpisodeIdsForGraph.includes(parentId)) {
|
|
4926
5271
|
threadEpisodeIdsForGraph.push(parentId);
|
|
4927
5272
|
}
|
|
@@ -4930,7 +5275,7 @@ var ExtractionPersistCoordinator = class {
|
|
|
4930
5275
|
}
|
|
4931
5276
|
if (!postWriteGuard2) {
|
|
4932
5277
|
try {
|
|
4933
|
-
await applyTemporalSupersession({
|
|
5278
|
+
const temporalSupersession = await applyTemporalSupersession({
|
|
4934
5279
|
storage: targetStorage,
|
|
4935
5280
|
newMemoryId: parentId,
|
|
4936
5281
|
entityRef: parentWriteEnvelope.entityRef,
|
|
@@ -4944,6 +5289,9 @@ var ExtractionPersistCoordinator = class {
|
|
|
4944
5289
|
config: this.config,
|
|
4945
5290
|
namespaceScope: this.deps.storageDirNamespace(targetStorage.dir)
|
|
4946
5291
|
});
|
|
5292
|
+
for (const supersededId of temporalSupersession.supersededIds) {
|
|
5293
|
+
await anchorSnapshots.remove(targetStorage, supersededId);
|
|
5294
|
+
}
|
|
4947
5295
|
} catch (err) {
|
|
4948
5296
|
log.warn(`temporal-supersession (chunked): unexpected error: ${err}`);
|
|
4949
5297
|
}
|
|
@@ -5111,7 +5459,15 @@ var ExtractionPersistCoordinator = class {
|
|
|
5111
5459
|
const tombstoneBlocked = factWrite.tombstoneBlocked;
|
|
5112
5460
|
const postWriteGuard = faithfulnessEnforceStatus === "pending_review" || tombstoneBlocked;
|
|
5113
5461
|
try {
|
|
5114
|
-
await this.deps.applyDeferredContradictionResolve(
|
|
5462
|
+
const contradictionOutcome = await this.deps.applyDeferredContradictionResolve(
|
|
5463
|
+
contradiction,
|
|
5464
|
+
targetStorage,
|
|
5465
|
+
memoryId,
|
|
5466
|
+
postWriteGuard
|
|
5467
|
+
);
|
|
5468
|
+
if (contradictionOutcome === "resolved" || contradictionOutcome === "lost_race") {
|
|
5469
|
+
await anchorSnapshots.remove(targetStorage, contradiction.supersededId);
|
|
5470
|
+
}
|
|
5115
5471
|
} catch (err) {
|
|
5116
5472
|
await flushDeferredFactHashOnFailure(() => this.deps.saveContentHashIndexes(), factDedupEnabled);
|
|
5117
5473
|
throw err;
|
|
@@ -5123,7 +5479,7 @@ var ExtractionPersistCoordinator = class {
|
|
|
5123
5479
|
}
|
|
5124
5480
|
if (!postWriteGuard) {
|
|
5125
5481
|
try {
|
|
5126
|
-
await applyTemporalSupersession({
|
|
5482
|
+
const temporalSupersession = await applyTemporalSupersession({
|
|
5127
5483
|
storage: targetStorage,
|
|
5128
5484
|
newMemoryId: memoryId,
|
|
5129
5485
|
entityRef: factWriteEnvelope.entityRef,
|
|
@@ -5134,6 +5490,9 @@ var ExtractionPersistCoordinator = class {
|
|
|
5134
5490
|
config: this.config,
|
|
5135
5491
|
namespaceScope: this.deps.storageDirNamespace(targetStorage.dir)
|
|
5136
5492
|
});
|
|
5493
|
+
for (const supersededId of temporalSupersession.supersededIds) {
|
|
5494
|
+
await anchorSnapshots.remove(targetStorage, supersededId);
|
|
5495
|
+
}
|
|
5137
5496
|
} catch (err) {
|
|
5138
5497
|
log.warn(`temporal-supersession: unexpected error: ${err}`);
|
|
5139
5498
|
}
|
|
@@ -5155,6 +5514,7 @@ var ExtractionPersistCoordinator = class {
|
|
|
5155
5514
|
category: writeCategory,
|
|
5156
5515
|
harmonicFact
|
|
5157
5516
|
});
|
|
5517
|
+
await anchorSnapshots.replace(targetStorage, memoryId, writeCategory, memoryPathById);
|
|
5158
5518
|
if (!postWriteGuard && threadEpisodeIdsForGraph && !threadEpisodeIdsForGraph.includes(memoryId)) {
|
|
5159
5519
|
threadEpisodeIdsForGraph.push(memoryId);
|
|
5160
5520
|
}
|
|
@@ -5398,12 +5758,256 @@ var ExtractionPersistCoordinator = class {
|
|
|
5398
5758
|
// src/orchestration/recall-internal.ts
|
|
5399
5759
|
import { createHash as createHash3 } from "crypto";
|
|
5400
5760
|
import { readFile as readFile2, stat, unlink } from "fs/promises";
|
|
5401
|
-
import
|
|
5761
|
+
import path9 from "path";
|
|
5762
|
+
|
|
5763
|
+
// src/orchestration/graph-path-state-loader.ts
|
|
5764
|
+
import { lstat, opendir, realpath } from "fs/promises";
|
|
5765
|
+
import path6 from "path";
|
|
5766
|
+
function isArchivePathIndexUnavailable(index) {
|
|
5767
|
+
return "unavailable" in index;
|
|
5768
|
+
}
|
|
5769
|
+
var MAX_ARCHIVE_PATH_INDEXES = 32;
|
|
5770
|
+
var MAX_ARCHIVE_PATH_INDEX_BUILDS = 32;
|
|
5771
|
+
var MAX_ARCHIVE_PATH_INDEX_GENERATION_RETRIES = 1;
|
|
5772
|
+
var MAX_ARCHIVE_INDEX_ENTRIES = 1e5;
|
|
5773
|
+
function isArchiveScanAbsenceError(error) {
|
|
5774
|
+
return isErrnoCode(error, "ENOENT") || isErrnoCode(error, "ENOTDIR");
|
|
5775
|
+
}
|
|
5776
|
+
var GraphPathStateLoader = class {
|
|
5777
|
+
archivePathIndexes;
|
|
5778
|
+
archivePathIndexBuilds = /* @__PURE__ */ new Map();
|
|
5779
|
+
archiveLstat = lstat;
|
|
5780
|
+
archiveRealpath = realpath;
|
|
5781
|
+
openArchiveDirectory = opendir;
|
|
5782
|
+
async readNode(storage, nodeId, deadlineAtMs, allowArchiveLookup) {
|
|
5783
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5784
|
+
const configuredStorageRoot = path6.resolve(storage.dir);
|
|
5785
|
+
const storageRoot = await realpath(configuredStorageRoot).catch(() => null);
|
|
5786
|
+
if (!storageRoot || storageRoot !== configuredStorageRoot) return null;
|
|
5787
|
+
const logicalId = path6.basename(nodeId, path6.extname(nodeId));
|
|
5788
|
+
const directRelativePaths = [nodeId, path6.join("cold", nodeId)];
|
|
5789
|
+
let inactiveDirectMemory = null;
|
|
5790
|
+
for (const relativePath of directRelativePaths) {
|
|
5791
|
+
const safePath = await this.resolveContainedPath(storageRoot, relativePath);
|
|
5792
|
+
if (!safePath) continue;
|
|
5793
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5794
|
+
const memory = await storage.readMemoryByPath(safePath);
|
|
5795
|
+
if (!memory || memory.frontmatter.id !== logicalId) continue;
|
|
5796
|
+
const inferredStatus = inferMemoryStatus(
|
|
5797
|
+
memory.frontmatter,
|
|
5798
|
+
toMemoryPathRel(storageRoot, safePath)
|
|
5799
|
+
);
|
|
5800
|
+
if (inferredStatus === "active") return memory;
|
|
5801
|
+
inactiveDirectMemory ??= memory;
|
|
5802
|
+
}
|
|
5803
|
+
if (inactiveDirectMemory) return inactiveDirectMemory;
|
|
5804
|
+
if (!allowArchiveLookup || typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) {
|
|
5805
|
+
return null;
|
|
5806
|
+
}
|
|
5807
|
+
const archiveIndex = await this.getArchivePathIndex(storage, storageRoot, deadlineAtMs);
|
|
5808
|
+
if (!archiveIndex || isArchivePathIndexUnavailable(archiveIndex) || typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) {
|
|
5809
|
+
return null;
|
|
5810
|
+
}
|
|
5811
|
+
const archivePaths = archiveIndex.pathsByBasename.get(path6.basename(nodeId)) ?? [];
|
|
5812
|
+
for (const archivePath of archivePaths) {
|
|
5813
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5814
|
+
const memory = await storage.readMemoryByPath(archivePath);
|
|
5815
|
+
if (!memory) continue;
|
|
5816
|
+
if (memory.frontmatter.id === logicalId) return memory;
|
|
5817
|
+
}
|
|
5818
|
+
return null;
|
|
5819
|
+
}
|
|
5820
|
+
async resolveContainedPath(storageRoot, relativePath) {
|
|
5821
|
+
if (path6.isAbsolute(relativePath)) return null;
|
|
5822
|
+
const rawSegments = relativePath.replace(/\\/g, "/").split("/");
|
|
5823
|
+
if (rawSegments.includes("..")) return null;
|
|
5824
|
+
const candidate = path6.resolve(storageRoot, relativePath);
|
|
5825
|
+
const lexicalRelative = path6.relative(storageRoot, candidate);
|
|
5826
|
+
if (lexicalRelative.length > 0 && (lexicalRelative.startsWith("..") || path6.isAbsolute(lexicalRelative))) {
|
|
5827
|
+
return null;
|
|
5828
|
+
}
|
|
5829
|
+
const canonical = await realpath(candidate).catch(() => candidate);
|
|
5830
|
+
const canonicalRelative = path6.relative(storageRoot, canonical);
|
|
5831
|
+
if (canonicalRelative.length > 0 && (canonicalRelative.startsWith("..") || path6.isAbsolute(canonicalRelative))) {
|
|
5832
|
+
return null;
|
|
5833
|
+
}
|
|
5834
|
+
return canonical;
|
|
5835
|
+
}
|
|
5836
|
+
async getArchivePathIndex(storage, storageRoot, deadlineAtMs) {
|
|
5837
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5838
|
+
if (!this.archivePathIndexes) this.archivePathIndexes = /* @__PURE__ */ new Map();
|
|
5839
|
+
const archivePathIndexes = this.archivePathIndexes;
|
|
5840
|
+
let generationRetries = 0;
|
|
5841
|
+
while (true) {
|
|
5842
|
+
const version = storage.getArchiveMutationVersion();
|
|
5843
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5844
|
+
const cacheKey = `${storageRoot}\0${version}`;
|
|
5845
|
+
const cached = archivePathIndexes.get(cacheKey);
|
|
5846
|
+
if (cached) {
|
|
5847
|
+
archivePathIndexes.delete(cacheKey);
|
|
5848
|
+
archivePathIndexes.set(cacheKey, cached);
|
|
5849
|
+
return cached;
|
|
5850
|
+
}
|
|
5851
|
+
let build = this.archivePathIndexBuilds.get(cacheKey);
|
|
5852
|
+
if (!build) {
|
|
5853
|
+
if (this.archivePathIndexBuilds.size >= MAX_ARCHIVE_PATH_INDEX_BUILDS) {
|
|
5854
|
+
const trackedBuilds = [...this.archivePathIndexBuilds.values()].map(
|
|
5855
|
+
(pending) => pending.then(() => void 0, () => void 0)
|
|
5856
|
+
);
|
|
5857
|
+
const admitted = await this.waitForDeadline(Promise.race(trackedBuilds), deadlineAtMs);
|
|
5858
|
+
if (admitted === null) return null;
|
|
5859
|
+
continue;
|
|
5860
|
+
}
|
|
5861
|
+
build = this.buildArchivePathIndex(storageRoot, version).then((index2) => {
|
|
5862
|
+
if (!index2) return null;
|
|
5863
|
+
if (storage.getArchiveMutationVersion() !== version) return null;
|
|
5864
|
+
const rootPrefix = `${storageRoot}\0`;
|
|
5865
|
+
for (const key of archivePathIndexes.keys()) {
|
|
5866
|
+
if (key.startsWith(rootPrefix)) archivePathIndexes.delete(key);
|
|
5867
|
+
}
|
|
5868
|
+
archivePathIndexes.set(cacheKey, index2);
|
|
5869
|
+
while (archivePathIndexes.size > MAX_ARCHIVE_PATH_INDEXES) {
|
|
5870
|
+
const oldestKey = archivePathIndexes.keys().next().value;
|
|
5871
|
+
if (oldestKey === void 0) break;
|
|
5872
|
+
archivePathIndexes.delete(oldestKey);
|
|
5873
|
+
}
|
|
5874
|
+
return index2;
|
|
5875
|
+
}).finally(() => {
|
|
5876
|
+
this.archivePathIndexBuilds.delete(cacheKey);
|
|
5877
|
+
});
|
|
5878
|
+
this.archivePathIndexBuilds.set(cacheKey, build);
|
|
5879
|
+
}
|
|
5880
|
+
const index = await this.waitForDeadline(build, deadlineAtMs);
|
|
5881
|
+
if (typeof deadlineAtMs === "number" && Date.now() >= deadlineAtMs) return null;
|
|
5882
|
+
const currentVersion = storage.getArchiveMutationVersion();
|
|
5883
|
+
if (index && currentVersion === version) return index;
|
|
5884
|
+
if (index && currentVersion !== version) archivePathIndexes.delete(cacheKey);
|
|
5885
|
+
if (currentVersion === version) return null;
|
|
5886
|
+
if (generationRetries >= MAX_ARCHIVE_PATH_INDEX_GENERATION_RETRIES) return null;
|
|
5887
|
+
generationRetries += 1;
|
|
5888
|
+
}
|
|
5889
|
+
}
|
|
5890
|
+
async waitForDeadline(promise, deadlineAtMs) {
|
|
5891
|
+
if (typeof deadlineAtMs !== "number") return promise;
|
|
5892
|
+
const remainingMs = deadlineAtMs - Date.now();
|
|
5893
|
+
if (remainingMs <= 0) return null;
|
|
5894
|
+
const timeout = Promise.withResolvers();
|
|
5895
|
+
const timer = setTimeout(() => timeout.resolve(null), remainingMs);
|
|
5896
|
+
try {
|
|
5897
|
+
return await Promise.race([promise, timeout.promise]);
|
|
5898
|
+
} finally {
|
|
5899
|
+
clearTimeout(timer);
|
|
5900
|
+
}
|
|
5901
|
+
}
|
|
5902
|
+
async buildArchivePathIndex(storageRoot, version) {
|
|
5903
|
+
const pathsByBasename = /* @__PURE__ */ new Map();
|
|
5904
|
+
const archiveRoot = path6.join(storageRoot, "archive");
|
|
5905
|
+
let archiveRootStatus;
|
|
5906
|
+
try {
|
|
5907
|
+
archiveRootStatus = await this.archiveLstat(archiveRoot);
|
|
5908
|
+
} catch (error) {
|
|
5909
|
+
if (isArchiveScanAbsenceError(error)) return { version, pathsByBasename };
|
|
5910
|
+
return null;
|
|
5911
|
+
}
|
|
5912
|
+
if (!archiveRootStatus || !archiveRootStatus.isDirectory() || archiveRootStatus.isSymbolicLink()) {
|
|
5913
|
+
return { version, pathsByBasename };
|
|
5914
|
+
}
|
|
5915
|
+
let canonicalArchiveRoot;
|
|
5916
|
+
try {
|
|
5917
|
+
canonicalArchiveRoot = await this.archiveRealpath(archiveRoot);
|
|
5918
|
+
} catch (error) {
|
|
5919
|
+
if (isArchiveScanAbsenceError(error)) return { version, pathsByBasename };
|
|
5920
|
+
return null;
|
|
5921
|
+
}
|
|
5922
|
+
const archiveRelative = path6.relative(storageRoot, canonicalArchiveRoot);
|
|
5923
|
+
if (archiveRelative.length > 0 && (archiveRelative.startsWith("..") || path6.isAbsolute(archiveRelative))) {
|
|
5924
|
+
return { version, pathsByBasename };
|
|
5925
|
+
}
|
|
5926
|
+
const pending = [canonicalArchiveRoot];
|
|
5927
|
+
let indexedPathCount = 0;
|
|
5928
|
+
let visitedEntryCount = 1;
|
|
5929
|
+
while (pending.length > 0) {
|
|
5930
|
+
const current = pending.pop();
|
|
5931
|
+
if (!current) break;
|
|
5932
|
+
let currentStatus;
|
|
5933
|
+
try {
|
|
5934
|
+
currentStatus = await this.archiveLstat(current);
|
|
5935
|
+
} catch (error) {
|
|
5936
|
+
if (isArchiveScanAbsenceError(error)) continue;
|
|
5937
|
+
return null;
|
|
5938
|
+
}
|
|
5939
|
+
if (!currentStatus || !currentStatus.isDirectory() || currentStatus.isSymbolicLink()) {
|
|
5940
|
+
continue;
|
|
5941
|
+
}
|
|
5942
|
+
let canonicalCurrent;
|
|
5943
|
+
try {
|
|
5944
|
+
canonicalCurrent = await this.archiveRealpath(current);
|
|
5945
|
+
} catch (error) {
|
|
5946
|
+
if (isArchiveScanAbsenceError(error)) continue;
|
|
5947
|
+
return null;
|
|
5948
|
+
}
|
|
5949
|
+
const currentRelative = path6.relative(storageRoot, canonicalCurrent);
|
|
5950
|
+
if (currentRelative.length > 0 && (currentRelative.startsWith("..") || path6.isAbsolute(currentRelative))) {
|
|
5951
|
+
continue;
|
|
5952
|
+
}
|
|
5953
|
+
let directory;
|
|
5954
|
+
try {
|
|
5955
|
+
directory = await this.openArchiveDirectory(canonicalCurrent);
|
|
5956
|
+
} catch (error) {
|
|
5957
|
+
if (isArchiveScanAbsenceError(error)) continue;
|
|
5958
|
+
return null;
|
|
5959
|
+
}
|
|
5960
|
+
try {
|
|
5961
|
+
for await (const entry of directory) {
|
|
5962
|
+
visitedEntryCount += 1;
|
|
5963
|
+
if (visitedEntryCount > MAX_ARCHIVE_INDEX_ENTRIES) {
|
|
5964
|
+
return { version, unavailable: "oversized" };
|
|
5965
|
+
}
|
|
5966
|
+
if (entry.isSymbolicLink()) continue;
|
|
5967
|
+
const entryPath = path6.join(canonicalCurrent, entry.name);
|
|
5968
|
+
if (entry.isDirectory()) {
|
|
5969
|
+
pending.push(entryPath);
|
|
5970
|
+
continue;
|
|
5971
|
+
}
|
|
5972
|
+
if (!entry.isFile() || !entry.name.endsWith(".md")) continue;
|
|
5973
|
+
if (indexedPathCount >= MAX_ARCHIVE_INDEX_ENTRIES) {
|
|
5974
|
+
return { version, unavailable: "oversized" };
|
|
5975
|
+
}
|
|
5976
|
+
let canonical;
|
|
5977
|
+
try {
|
|
5978
|
+
canonical = await this.archiveRealpath(entryPath);
|
|
5979
|
+
} catch (error) {
|
|
5980
|
+
if (isArchiveScanAbsenceError(error)) continue;
|
|
5981
|
+
return null;
|
|
5982
|
+
}
|
|
5983
|
+
const relative = path6.relative(storageRoot, canonical);
|
|
5984
|
+
if (relative.length > 0 && (relative.startsWith("..") || path6.isAbsolute(relative))) {
|
|
5985
|
+
continue;
|
|
5986
|
+
}
|
|
5987
|
+
const paths = pathsByBasename.get(entry.name);
|
|
5988
|
+
if (paths) paths.push(canonical);
|
|
5989
|
+
else pathsByBasename.set(entry.name, [canonical]);
|
|
5990
|
+
indexedPathCount += 1;
|
|
5991
|
+
}
|
|
5992
|
+
} catch {
|
|
5993
|
+
return null;
|
|
5994
|
+
}
|
|
5995
|
+
}
|
|
5996
|
+
for (const paths of pathsByBasename.values()) {
|
|
5997
|
+
paths.sort((left, right) => {
|
|
5998
|
+
const normalizedLeft = left.normalize("NFC");
|
|
5999
|
+
const normalizedRight = right.normalize("NFC");
|
|
6000
|
+
return normalizedRight < normalizedLeft ? -1 : normalizedRight > normalizedLeft ? 1 : 0;
|
|
6001
|
+
});
|
|
6002
|
+
}
|
|
6003
|
+
return { version, pathsByBasename };
|
|
6004
|
+
}
|
|
6005
|
+
};
|
|
5402
6006
|
|
|
5403
6007
|
// src/orchestration/graph-recall-coordinator.ts
|
|
5404
6008
|
import { createHash as createHash2 } from "crypto";
|
|
5405
6009
|
import { mkdir as mkdir3, writeFile as writeFile3 } from "fs/promises";
|
|
5406
|
-
import
|
|
6010
|
+
import path7 from "path";
|
|
5407
6011
|
function mergeGraphExpandedResults(primary, expanded) {
|
|
5408
6012
|
const mergedByNamespaceAndPath = /* @__PURE__ */ new Map();
|
|
5409
6013
|
for (const item of [...primary, ...expanded]) {
|
|
@@ -5420,11 +6024,11 @@ function mergeGraphExpandedResults(primary, expanded) {
|
|
|
5420
6024
|
return Array.from(mergedByNamespaceAndPath.values());
|
|
5421
6025
|
}
|
|
5422
6026
|
function graphPathRelativeToStorage(storageDir, candidatePath) {
|
|
5423
|
-
const absolutePath =
|
|
5424
|
-
const rel =
|
|
6027
|
+
const absolutePath = path7.isAbsolute(candidatePath) ? candidatePath : path7.resolve(storageDir, candidatePath);
|
|
6028
|
+
const rel = path7.relative(storageDir, absolutePath);
|
|
5425
6029
|
if (!rel || rel === ".") return null;
|
|
5426
6030
|
if (rel.startsWith("..")) return null;
|
|
5427
|
-
return rel.split(
|
|
6031
|
+
return rel.split(path7.sep).join("/");
|
|
5428
6032
|
}
|
|
5429
6033
|
function normalizeGraphActivationScore(score) {
|
|
5430
6034
|
const bounded = Number.isFinite(score) && score > 0 ? score : 0;
|
|
@@ -5441,6 +6045,19 @@ function blendGraphExpandedRecallScore(options) {
|
|
|
5441
6045
|
const blended = graphNorm * weight + seedScore * (1 - weight);
|
|
5442
6046
|
return Math.max(minBound, Math.min(maxBound, blended));
|
|
5443
6047
|
}
|
|
6048
|
+
var KNOWN_PATH_NODE_STATUSES = {
|
|
6049
|
+
active: true,
|
|
6050
|
+
pending_review: true,
|
|
6051
|
+
rejected: true,
|
|
6052
|
+
quarantined: true,
|
|
6053
|
+
superseded: true,
|
|
6054
|
+
archived: true,
|
|
6055
|
+
forgotten: true
|
|
6056
|
+
};
|
|
6057
|
+
function normalizeInferredPathNodeStatus(value) {
|
|
6058
|
+
if (typeof value !== "string" || KNOWN_PATH_NODE_STATUSES[value] !== true) return null;
|
|
6059
|
+
return value;
|
|
6060
|
+
}
|
|
5444
6061
|
var GraphRecallCoordinator = class {
|
|
5445
6062
|
getConfig;
|
|
5446
6063
|
getStorage;
|
|
@@ -5450,6 +6067,7 @@ var GraphRecallCoordinator = class {
|
|
|
5450
6067
|
resolveColdQmdResultForRecall;
|
|
5451
6068
|
storageForAbsoluteQmdResultPath;
|
|
5452
6069
|
readQmdResultMemory;
|
|
6070
|
+
graphPathStateLoader = new GraphPathStateLoader();
|
|
5453
6071
|
constructor(options) {
|
|
5454
6072
|
this.getConfig = options.getConfig;
|
|
5455
6073
|
this.getStorage = options.getStorage;
|
|
@@ -5462,6 +6080,21 @@ var GraphRecallCoordinator = class {
|
|
|
5462
6080
|
}
|
|
5463
6081
|
async expandResultsViaGraph(options) {
|
|
5464
6082
|
const config = this.getConfig();
|
|
6083
|
+
const parsedAsOfMs = typeof options.asOf === "string" ? Date.parse(options.asOf) : Number.NaN;
|
|
6084
|
+
const hasHistoricalAsOf = Number.isFinite(parsedAsOfMs) || typeof options.asOfMs === "number" && Number.isFinite(options.asOfMs);
|
|
6085
|
+
const effectiveAsOfMs = Number.isFinite(parsedAsOfMs) ? parsedAsOfMs : typeof options.asOfMs === "number" && Number.isFinite(options.asOfMs) ? options.asOfMs : Date.now();
|
|
6086
|
+
const effectiveAsOf = new Date(effectiveAsOfMs).toISOString();
|
|
6087
|
+
const isEligibleGraphCandidate = (memory, storageDir) => {
|
|
6088
|
+
if (hasHistoricalAsOf && !isValidAsOf(memory.frontmatter, effectiveAsOfMs)) {
|
|
6089
|
+
return false;
|
|
6090
|
+
}
|
|
6091
|
+
if (!hasHistoricalAsOf && config.temporalBiTemporal === true && config.temporalExpiredInInjection !== true && isValidityExpiredNow(memory.frontmatter, Date.now())) {
|
|
6092
|
+
return false;
|
|
6093
|
+
}
|
|
6094
|
+
const lifecyclePath = toMemoryPathRel(storageDir, memory.path);
|
|
6095
|
+
const status = inferMemoryStatus(memory.frontmatter, lifecyclePath);
|
|
6096
|
+
return status === "active" || status === "superseded" && hasHistoricalAsOf;
|
|
6097
|
+
};
|
|
5465
6098
|
const deadlineExpired = () => typeof options.deadlineAtMs === "number" && Date.now() >= options.deadlineAtMs;
|
|
5466
6099
|
const byNamespace = /* @__PURE__ */ new Map();
|
|
5467
6100
|
const addResultForNamespace = (namespace, result) => {
|
|
@@ -5495,7 +6128,7 @@ var GraphRecallCoordinator = class {
|
|
|
5495
6128
|
resolvedPath = resolvedCold.result.path;
|
|
5496
6129
|
resolvedResult = resolvedCold.result;
|
|
5497
6130
|
}
|
|
5498
|
-
if (!
|
|
6131
|
+
if (!path7.isAbsolute(resolvedPath)) {
|
|
5499
6132
|
resolvedAmbiguousSeeds.set(result.path, null);
|
|
5500
6133
|
return null;
|
|
5501
6134
|
}
|
|
@@ -5520,7 +6153,7 @@ var GraphRecallCoordinator = class {
|
|
|
5520
6153
|
}
|
|
5521
6154
|
continue;
|
|
5522
6155
|
}
|
|
5523
|
-
if (
|
|
6156
|
+
if (path7.isAbsolute(result.path)) {
|
|
5524
6157
|
const resolved = await resolveAmbiguousSeedOwner(result, null);
|
|
5525
6158
|
if (resolved) {
|
|
5526
6159
|
addResultForNamespace(resolved.namespace, resolved.result);
|
|
@@ -5533,6 +6166,11 @@ var GraphRecallCoordinator = class {
|
|
|
5533
6166
|
}
|
|
5534
6167
|
const perNamespaceSeedCap = Math.max(3, options.recallResultLimit);
|
|
5535
6168
|
const perNamespaceExpandedCap = Math.max(8, options.recallResultLimit * 2);
|
|
6169
|
+
const graphPathStateLoadLimit = Math.min(
|
|
6170
|
+
200,
|
|
6171
|
+
perNamespaceExpandedCap + Math.max(8, perNamespaceExpandedCap * 4)
|
|
6172
|
+
);
|
|
6173
|
+
const graphCandidateScanLimit = hasHistoricalAsOf ? 200 : graphPathStateLoadLimit;
|
|
5536
6174
|
const seedPaths = [];
|
|
5537
6175
|
const seedResults = [];
|
|
5538
6176
|
const expandedPaths = [];
|
|
@@ -5549,9 +6187,7 @@ var GraphRecallCoordinator = class {
|
|
|
5549
6187
|
[namespace]
|
|
5550
6188
|
) : (await Promise.all(
|
|
5551
6189
|
seedCandidates.map(
|
|
5552
|
-
(result) => this.graphSeedPathRelativeToStorage(storage, result, [
|
|
5553
|
-
namespace
|
|
5554
|
-
])
|
|
6190
|
+
(result) => this.graphSeedPathRelativeToStorage(storage, result, [namespace])
|
|
5555
6191
|
)
|
|
5556
6192
|
)).filter(
|
|
5557
6193
|
(value) => typeof value === "string" && value.length > 0
|
|
@@ -5563,61 +6199,168 @@ var GraphRecallCoordinator = class {
|
|
|
5563
6199
|
0
|
|
5564
6200
|
);
|
|
5565
6201
|
seedPaths.push(
|
|
5566
|
-
...seedRelativePaths.map((rel) =>
|
|
6202
|
+
...seedRelativePaths.map((rel) => path7.join(storage.dir, rel))
|
|
5567
6203
|
);
|
|
5568
6204
|
const seedSet = new Set(seedRelativePaths);
|
|
6205
|
+
const nodeMemoryCache = /* @__PURE__ */ new Map();
|
|
6206
|
+
const readGraphNode = async (nodeId, allowArchiveLookup) => {
|
|
6207
|
+
if (nodeMemoryCache.has(nodeId)) return nodeMemoryCache.get(nodeId) ?? null;
|
|
6208
|
+
const memory = await this.graphPathStateLoader.readNode(
|
|
6209
|
+
storage,
|
|
6210
|
+
nodeId,
|
|
6211
|
+
options.deadlineAtMs,
|
|
6212
|
+
allowArchiveLookup
|
|
6213
|
+
);
|
|
6214
|
+
nodeMemoryCache.set(nodeId, memory);
|
|
6215
|
+
return memory;
|
|
6216
|
+
};
|
|
6217
|
+
const scoringEnabled = config.graphPathScoring.enabled;
|
|
5569
6218
|
const expanded = await this.graphIndexFor(storage).spreadingActivation(
|
|
5570
6219
|
seedRelativePaths,
|
|
5571
6220
|
config.maxGraphTraversalSteps,
|
|
5572
6221
|
{
|
|
5573
6222
|
...options.includeLowConfidence === true ? { includeLowConfidence: true } : {},
|
|
6223
|
+
...scoringEnabled ? { recordPaths: true } : {},
|
|
5574
6224
|
...typeof options.deadlineAtMs === "number" ? { deadlineAtMs: options.deadlineAtMs } : {}
|
|
5575
6225
|
}
|
|
5576
6226
|
);
|
|
5577
6227
|
if (expanded.length === 0) continue;
|
|
5578
6228
|
if (deadlineExpired()) break;
|
|
5579
|
-
|
|
6229
|
+
if (!scoringEnabled) {
|
|
6230
|
+
let eligibleCount = 0;
|
|
6231
|
+
for (const candidate of expanded.slice(0, graphCandidateScanLimit)) {
|
|
6232
|
+
if (seedSet.has(candidate.path)) continue;
|
|
6233
|
+
const memory = await readGraphNode(candidate.path, false);
|
|
6234
|
+
if (deadlineExpired()) break;
|
|
6235
|
+
if (!memory) continue;
|
|
6236
|
+
if (/(?:^|[\\/])artifacts(?:[\\/]|$)/i.test(memory.path)) continue;
|
|
6237
|
+
if (!isEligibleGraphCandidate(memory, storage.dir)) continue;
|
|
6238
|
+
const score = blendGraphExpandedRecallScore({
|
|
6239
|
+
graphActivationScore: candidate.score,
|
|
6240
|
+
seedRecallScore,
|
|
6241
|
+
activationWeight: config.graphExpansionActivationWeight,
|
|
6242
|
+
blendMin: config.graphExpansionBlendMin,
|
|
6243
|
+
blendMax: config.graphExpansionBlendMax
|
|
6244
|
+
});
|
|
6245
|
+
expandedResults.push({
|
|
6246
|
+
docid: memory.frontmatter.id,
|
|
6247
|
+
path: memory.path,
|
|
6248
|
+
namespace,
|
|
6249
|
+
snippet: memory.content.slice(0, 400),
|
|
6250
|
+
score
|
|
6251
|
+
});
|
|
6252
|
+
expandedPaths.push({
|
|
6253
|
+
path: memory.path,
|
|
6254
|
+
score,
|
|
6255
|
+
namespace,
|
|
6256
|
+
seed: path7.resolve(storage.dir, candidate.seed),
|
|
6257
|
+
hopDepth: candidate.hopDepth,
|
|
6258
|
+
decayedWeight: candidate.decayedWeight,
|
|
6259
|
+
graphType: candidate.graphType,
|
|
6260
|
+
edgeConfidence: candidate.edgeConfidence
|
|
6261
|
+
});
|
|
6262
|
+
eligibleCount += 1;
|
|
6263
|
+
if (eligibleCount >= perNamespaceExpandedCap) break;
|
|
6264
|
+
}
|
|
6265
|
+
continue;
|
|
6266
|
+
}
|
|
6267
|
+
const nodeStates = /* @__PURE__ */ new Map();
|
|
6268
|
+
const addState = (memory) => {
|
|
6269
|
+
const relativePath = graphPathRelativeToStorage(storage.dir, memory.path);
|
|
6270
|
+
const lifecyclePath = toMemoryPathRel(storage.dir, memory.path);
|
|
6271
|
+
const state = {
|
|
6272
|
+
id: memory.frontmatter.id,
|
|
6273
|
+
status: normalizeInferredPathNodeStatus(
|
|
6274
|
+
inferMemoryStatus(memory.frontmatter, lifecyclePath)
|
|
6275
|
+
),
|
|
6276
|
+
created: memory.frontmatter.created,
|
|
6277
|
+
valid_at: memory.frontmatter.valid_at,
|
|
6278
|
+
invalid_at: memory.frontmatter.invalid_at,
|
|
6279
|
+
supersededAt: memory.frontmatter.supersededAt,
|
|
6280
|
+
eventTimeSource: memory.frontmatter.eventTimeSource
|
|
6281
|
+
};
|
|
6282
|
+
const add = (key) => {
|
|
6283
|
+
if (!nodeStates.has(key)) nodeStates.set(key, state);
|
|
6284
|
+
};
|
|
6285
|
+
add(memory.frontmatter.id);
|
|
6286
|
+
if (relativePath) {
|
|
6287
|
+
add(relativePath);
|
|
6288
|
+
if (relativePath.endsWith(".md")) add(path7.basename(relativePath, ".md"));
|
|
6289
|
+
}
|
|
6290
|
+
return state;
|
|
6291
|
+
};
|
|
6292
|
+
const scoredExpanded = [];
|
|
6293
|
+
for (const candidate of expanded.slice(0, graphCandidateScanLimit)) {
|
|
5580
6294
|
if (deadlineExpired()) break;
|
|
5581
6295
|
if (seedSet.has(candidate.path)) continue;
|
|
5582
|
-
const
|
|
5583
|
-
const memory = await storage.readMemoryByPath(memoryPath);
|
|
6296
|
+
const memory = await readGraphNode(candidate.path, true);
|
|
5584
6297
|
if (deadlineExpired()) break;
|
|
5585
6298
|
if (!memory) continue;
|
|
5586
6299
|
if (/(?:^|[\\/])artifacts(?:[\\/]|$)/i.test(memory.path)) continue;
|
|
5587
|
-
if (memory
|
|
5588
|
-
|
|
5589
|
-
|
|
5590
|
-
|
|
6300
|
+
if (!isEligibleGraphCandidate(memory, storage.dir)) continue;
|
|
6301
|
+
if (candidate.activationPath) {
|
|
6302
|
+
for (const nodeId of candidate.activationPath.nodeIds.slice(1, -1)) {
|
|
6303
|
+
if (deadlineExpired()) break;
|
|
6304
|
+
const intermediate = await readGraphNode(nodeId, true);
|
|
6305
|
+
if (deadlineExpired()) break;
|
|
6306
|
+
if (!intermediate) {
|
|
6307
|
+
log.debug(`graph path scoring missing intermediate memory state: ${nodeId}`);
|
|
6308
|
+
continue;
|
|
6309
|
+
}
|
|
6310
|
+
const state = addState(intermediate);
|
|
6311
|
+
nodeStates.set(nodeId, { ...state, id: nodeId });
|
|
6312
|
+
}
|
|
6313
|
+
if (deadlineExpired()) break;
|
|
6314
|
+
}
|
|
6315
|
+
const pathScoreDetail = scoreEvidencePathDetail(
|
|
6316
|
+
candidate.activationPath ?? null,
|
|
6317
|
+
nodeStates,
|
|
6318
|
+
{
|
|
6319
|
+
asOf: effectiveAsOf,
|
|
6320
|
+
invalidNodePenalty: config.graphPathScoring.invalidNodePenalty
|
|
6321
|
+
}
|
|
6322
|
+
);
|
|
6323
|
+
const blendedScore = blendGraphExpandedRecallScore({
|
|
5591
6324
|
graphActivationScore: candidate.score,
|
|
5592
6325
|
seedRecallScore,
|
|
5593
6326
|
activationWeight: config.graphExpansionActivationWeight,
|
|
5594
6327
|
blendMin: config.graphExpansionBlendMin,
|
|
5595
6328
|
blendMax: config.graphExpansionBlendMax
|
|
5596
6329
|
});
|
|
5597
|
-
|
|
5598
|
-
|
|
5599
|
-
// Absolute path, matching the globally-unique identity of primary
|
|
5600
|
-
// fanout hits, so the merge dedups a memory found by both (#2020).
|
|
5601
|
-
path: memory.path,
|
|
5602
|
-
namespace,
|
|
5603
|
-
snippet,
|
|
5604
|
-
score
|
|
5605
|
-
});
|
|
5606
|
-
expandedPaths.push({
|
|
6330
|
+
const score = blendedScore * pathScoreDetail.score;
|
|
6331
|
+
const entry = {
|
|
5607
6332
|
path: memory.path,
|
|
5608
6333
|
score,
|
|
5609
6334
|
namespace,
|
|
5610
|
-
seed:
|
|
6335
|
+
seed: path7.resolve(storage.dir, candidate.seed),
|
|
5611
6336
|
hopDepth: candidate.hopDepth,
|
|
5612
6337
|
decayedWeight: candidate.decayedWeight,
|
|
5613
6338
|
graphType: candidate.graphType,
|
|
5614
|
-
|
|
5615
|
-
|
|
5616
|
-
|
|
5617
|
-
|
|
5618
|
-
|
|
6339
|
+
edgeConfidence: candidate.edgeConfidence,
|
|
6340
|
+
pathPenaltyApplied: pathScoreDetail.pathPenaltyApplied,
|
|
6341
|
+
...config.graphPathScoring.includePathInProvenance && candidate.activationPath ? { pathNodeIds: candidate.activationPath.nodeIds } : {}
|
|
6342
|
+
};
|
|
6343
|
+
scoredExpanded.push({
|
|
6344
|
+
result: {
|
|
6345
|
+
docid: memory.frontmatter.id,
|
|
6346
|
+
path: memory.path,
|
|
6347
|
+
namespace,
|
|
6348
|
+
snippet: memory.content.slice(0, 400),
|
|
6349
|
+
score,
|
|
6350
|
+
pathPenaltyApplied: pathScoreDetail.pathPenaltyApplied,
|
|
6351
|
+
...config.graphPathScoring.includePathInProvenance && candidate.activationPath ? { pathNodeIds: candidate.activationPath.nodeIds } : {}
|
|
6352
|
+
},
|
|
6353
|
+
entry
|
|
5619
6354
|
});
|
|
5620
6355
|
}
|
|
6356
|
+
scoredExpanded.sort((a, b) => {
|
|
6357
|
+
if (a.result.score !== b.result.score) return a.result.score > b.result.score ? -1 : 1;
|
|
6358
|
+
return a.result.path < b.result.path ? -1 : a.result.path > b.result.path ? 1 : 0;
|
|
6359
|
+
});
|
|
6360
|
+
for (const item of scoredExpanded.slice(0, perNamespaceExpandedCap)) {
|
|
6361
|
+
expandedResults.push(item.result);
|
|
6362
|
+
expandedPaths.push(item.entry);
|
|
6363
|
+
}
|
|
5621
6364
|
}
|
|
5622
6365
|
const namespacedPrimaryResults = Array.from(byNamespace.entries()).flatMap(
|
|
5623
6366
|
([namespace, results]) => results.map((result) => ({ ...result, namespace }))
|
|
@@ -5631,12 +6374,12 @@ var GraphRecallCoordinator = class {
|
|
|
5631
6374
|
}
|
|
5632
6375
|
async recordLastGraphRecallSnapshot(options) {
|
|
5633
6376
|
try {
|
|
5634
|
-
const snapshotPath =
|
|
6377
|
+
const snapshotPath = path7.join(
|
|
5635
6378
|
options.storage.dir,
|
|
5636
6379
|
"state",
|
|
5637
6380
|
"last_graph_recall.json"
|
|
5638
6381
|
);
|
|
5639
|
-
await mkdir3(
|
|
6382
|
+
await mkdir3(path7.dirname(snapshotPath), { recursive: true });
|
|
5640
6383
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
5641
6384
|
const totalSeedCount = options.seedPaths.length;
|
|
5642
6385
|
const totalExpandedCount = options.expandedPaths.length;
|
|
@@ -5751,11 +6494,11 @@ ${blocks.join("\n\n")}`;
|
|
|
5751
6494
|
}
|
|
5752
6495
|
|
|
5753
6496
|
// src/orchestration/recall-profile-storage.ts
|
|
5754
|
-
import
|
|
6497
|
+
import path8 from "path";
|
|
5755
6498
|
function resolveCompositeProfileStorage(options) {
|
|
5756
6499
|
const { profileStorages, memoryDir } = options;
|
|
5757
6500
|
const emptyProfileStorage = new Proxy(
|
|
5758
|
-
{ dir:
|
|
6501
|
+
{ dir: path8.join(memoryDir, ".empty-scope-profile") },
|
|
5759
6502
|
{
|
|
5760
6503
|
get(target, prop) {
|
|
5761
6504
|
if (prop in target) return Reflect.get(target, prop);
|
|
@@ -6132,7 +6875,7 @@ var RecallInternalCoordinator = class {
|
|
|
6132
6875
|
const graphExpandedResultPaths = /* @__PURE__ */ new Set();
|
|
6133
6876
|
const graphSourceLabelsForPath = (resultPath) => {
|
|
6134
6877
|
const labels = [];
|
|
6135
|
-
const normalizedPath = resultPath.split(
|
|
6878
|
+
const normalizedPath = resultPath.split(path9.sep).join("/");
|
|
6136
6879
|
const isEntityPath = normalizedPath.startsWith("entities/") || normalizedPath.includes("/entities/");
|
|
6137
6880
|
if (graphBaselinePaths.has(resultPath)) labels.push("baseline");
|
|
6138
6881
|
if (graphExpandedResultPaths.has(resultPath))
|
|
@@ -7649,11 +8392,11 @@ ${formatted}`;
|
|
|
7649
8392
|
if (!resolveRecallAuxiliaryCapabilities(this.deps.config).compactionReset) return null;
|
|
7650
8393
|
const workspaceDir = compactionWorkspaceDir || this.deps.config.workspaceDir || defaultWorkspaceDir();
|
|
7651
8394
|
const safeSessionKey = sanitizeSessionKeyForFilename(effectiveSessionKey);
|
|
7652
|
-
const signalPath =
|
|
8395
|
+
const signalPath = path9.join(
|
|
7653
8396
|
workspaceDir,
|
|
7654
8397
|
`.compaction-reset-signal-${safeSessionKey}`
|
|
7655
8398
|
);
|
|
7656
|
-
const bootPath =
|
|
8399
|
+
const bootPath = path9.join(workspaceDir, "BOOT.md");
|
|
7657
8400
|
try {
|
|
7658
8401
|
const signalStat = await stat(signalPath).catch(() => null);
|
|
7659
8402
|
if (!signalStat) return null;
|
|
@@ -8618,7 +9361,8 @@ ${tmtNode.summary}`
|
|
|
8618
9361
|
recallNamespaces,
|
|
8619
9362
|
recallResultLimit,
|
|
8620
9363
|
deadlineAtMs: enrichmentAssemblyDeadlineAtMs,
|
|
8621
|
-
...options.includeLowConfidence === true ? { includeLowConfidence: true } : {}
|
|
9364
|
+
...options.includeLowConfidence === true ? { includeLowConfidence: true } : {},
|
|
9365
|
+
...typeof asOfMs === "number" ? { asOfMs } : {}
|
|
8622
9366
|
}),
|
|
8623
9367
|
null
|
|
8624
9368
|
);
|
|
@@ -9691,6 +10435,8 @@ ${tmtNode.summary}`
|
|
|
9691
10435
|
servedBy,
|
|
9692
10436
|
scoreDecomposition,
|
|
9693
10437
|
admittedBy: [],
|
|
10438
|
+
...xrayResult?.pathNodeIds ? { pathNodeIds: xrayResult.pathNodeIds } : {},
|
|
10439
|
+
...typeof xrayResult?.pathPenaltyApplied === "boolean" ? { pathPenaltyApplied: xrayResult.pathPenaltyApplied } : {},
|
|
9694
10440
|
...provenance ? { provenance } : {},
|
|
9695
10441
|
...sourceSpan ? { sourceSpan } : {},
|
|
9696
10442
|
// Issue #1577 — per-result trust projection for X-ray visibility.
|
|
@@ -9885,10 +10631,10 @@ ${tmtNode.summary}`
|
|
|
9885
10631
|
|
|
9886
10632
|
// src/orchestration/recall-search-pipeline.ts
|
|
9887
10633
|
import { createHash as createHash4 } from "crypto";
|
|
9888
|
-
import
|
|
10634
|
+
import path11 from "path";
|
|
9889
10635
|
|
|
9890
10636
|
// src/orchestration/recall-search-prefilter.ts
|
|
9891
|
-
import
|
|
10637
|
+
import path10 from "path";
|
|
9892
10638
|
async function fetchActiveArtifactsForNamespace(deps, namespace, prompt, targetCount, options = {}) {
|
|
9893
10639
|
const storage = await deps.storageRouter.storageFor(namespace);
|
|
9894
10640
|
let fetchLimit = computeArtifactCandidateFetchLimit(targetCount);
|
|
@@ -10017,7 +10763,7 @@ async function searchEmbeddingFallback(deps, query, limit) {
|
|
|
10017
10763
|
if (hits.length === 0) return [];
|
|
10018
10764
|
const results = [];
|
|
10019
10765
|
for (const hit of hits) {
|
|
10020
|
-
const fullPath =
|
|
10766
|
+
const fullPath = path10.isAbsolute(hit.path) ? hit.path : path10.join(deps.config.memoryDir, hit.path);
|
|
10021
10767
|
const memory = await deps.storage.readMemoryByPath(fullPath);
|
|
10022
10768
|
if (!memory) continue;
|
|
10023
10769
|
results.push({
|
|
@@ -10385,7 +11131,7 @@ var RecallSearchPipelineCoordinator = class {
|
|
|
10385
11131
|
const storage = await this.deps.storageRouter.storageFor(namespace);
|
|
10386
11132
|
const storageDir = typeof storage.dir === "string" && storage.dir ? storage.dir : null;
|
|
10387
11133
|
if (!storageDir) continue;
|
|
10388
|
-
const recallRoot =
|
|
11134
|
+
const recallRoot = path11.resolve(storageDir);
|
|
10389
11135
|
if (seenRecallRoots.has(recallRoot)) continue;
|
|
10390
11136
|
seenRecallRoots.add(recallRoot);
|
|
10391
11137
|
recallRoots.push(recallRoot);
|
|
@@ -10409,8 +11155,8 @@ var RecallSearchPipelineCoordinator = class {
|
|
|
10409
11155
|
if (resolvedCold) scopedResults.push(resolvedCold.result);
|
|
10410
11156
|
continue;
|
|
10411
11157
|
}
|
|
10412
|
-
if (
|
|
10413
|
-
if (recallRoots.some((recallRoot) => isPathInsideStorageRoot(recallRoot,
|
|
11158
|
+
if (path11.isAbsolute(result.path)) {
|
|
11159
|
+
if (recallRoots.some((recallRoot) => isPathInsideStorageRoot(recallRoot, path11.resolve(result.path)))) {
|
|
10414
11160
|
scopedResults.push(result);
|
|
10415
11161
|
}
|
|
10416
11162
|
continue;
|
|
@@ -10429,7 +11175,8 @@ var RecallSearchPipelineCoordinator = class {
|
|
|
10429
11175
|
recallNamespaces: options.recallNamespaces,
|
|
10430
11176
|
recallResultLimit: options.recallResultLimit,
|
|
10431
11177
|
deadlineAtMs: options.deadlineAtMs,
|
|
10432
|
-
...options.includeLowConfidence === true ? { includeLowConfidence: true } : {}
|
|
11178
|
+
...options.includeLowConfidence === true ? { includeLowConfidence: true } : {},
|
|
11179
|
+
...typeof options.asOfMs === "number" ? { asOfMs: options.asOfMs } : {}
|
|
10433
11180
|
});
|
|
10434
11181
|
results = merged;
|
|
10435
11182
|
}
|
|
@@ -11499,7 +12246,7 @@ var TurnIngestionCoordinator = class {
|
|
|
11499
12246
|
|
|
11500
12247
|
// src/orchestration/recall-introspection.ts
|
|
11501
12248
|
import { mkdir as mkdir5, readFile as readFile4, writeFile as writeFile5 } from "fs/promises";
|
|
11502
|
-
import
|
|
12249
|
+
import path13 from "path";
|
|
11503
12250
|
|
|
11504
12251
|
// src/taxonomy/default-taxonomy.ts
|
|
11505
12252
|
var DEFAULT_TAXONOMY = {
|
|
@@ -11622,7 +12369,7 @@ function generateResolverDocument(taxonomy) {
|
|
|
11622
12369
|
|
|
11623
12370
|
// src/taxonomy/taxonomy-loader.ts
|
|
11624
12371
|
import { readFile as readFile3, mkdir as mkdir4, writeFile as writeFile4 } from "fs/promises";
|
|
11625
|
-
import
|
|
12372
|
+
import path12 from "path";
|
|
11626
12373
|
var TAXONOMY_DIR = ".taxonomy";
|
|
11627
12374
|
var TAXONOMY_FILE = "taxonomy.json";
|
|
11628
12375
|
var MAX_SLUG_LENGTH = 32;
|
|
@@ -11720,7 +12467,7 @@ function validateTaxonomy(taxonomy) {
|
|
|
11720
12467
|
}
|
|
11721
12468
|
}
|
|
11722
12469
|
async function loadTaxonomy(memoryDir) {
|
|
11723
|
-
const taxonomyPath =
|
|
12470
|
+
const taxonomyPath = path12.join(memoryDir, TAXONOMY_DIR, TAXONOMY_FILE);
|
|
11724
12471
|
let raw;
|
|
11725
12472
|
try {
|
|
11726
12473
|
raw = await readFile3(taxonomyPath, "utf-8");
|
|
@@ -11770,16 +12517,16 @@ async function loadTaxonomy(memoryDir) {
|
|
|
11770
12517
|
}
|
|
11771
12518
|
async function saveTaxonomy(memoryDir, taxonomy) {
|
|
11772
12519
|
validateTaxonomy(taxonomy);
|
|
11773
|
-
const dir =
|
|
12520
|
+
const dir = path12.join(memoryDir, TAXONOMY_DIR);
|
|
11774
12521
|
await mkdir4(dir, { recursive: true });
|
|
11775
|
-
const filePath =
|
|
12522
|
+
const filePath = path12.join(dir, TAXONOMY_FILE);
|
|
11776
12523
|
await writeFile4(filePath, JSON.stringify(taxonomy, null, 2) + "\n", "utf-8");
|
|
11777
12524
|
}
|
|
11778
12525
|
function getTaxonomyDir(memoryDir) {
|
|
11779
|
-
return
|
|
12526
|
+
return path12.join(memoryDir, TAXONOMY_DIR);
|
|
11780
12527
|
}
|
|
11781
12528
|
function getTaxonomyFilePath(memoryDir) {
|
|
11782
|
-
return
|
|
12529
|
+
return path12.join(memoryDir, TAXONOMY_DIR, TAXONOMY_FILE);
|
|
11783
12530
|
}
|
|
11784
12531
|
|
|
11785
12532
|
// src/orchestration/recall-introspection.ts
|
|
@@ -11803,7 +12550,7 @@ var RecallIntrospectionCoordinator = class {
|
|
|
11803
12550
|
}
|
|
11804
12551
|
async getLastGraphRecallSnapshot(namespace) {
|
|
11805
12552
|
const storage = await this.deps.getStorage(namespace);
|
|
11806
|
-
const snapshotPath =
|
|
12553
|
+
const snapshotPath = path13.join(
|
|
11807
12554
|
storage.dir,
|
|
11808
12555
|
"state",
|
|
11809
12556
|
"last_graph_recall.json"
|
|
@@ -11842,7 +12589,7 @@ var RecallIntrospectionCoordinator = class {
|
|
|
11842
12589
|
}
|
|
11843
12590
|
async getLastIntentSnapshot(namespace) {
|
|
11844
12591
|
const storage = await this.deps.getStorage(namespace);
|
|
11845
|
-
const snapshotPath =
|
|
12592
|
+
const snapshotPath = path13.join(storage.dir, "state", "last_intent.json");
|
|
11846
12593
|
try {
|
|
11847
12594
|
const raw = await readFile4(snapshotPath, "utf-8");
|
|
11848
12595
|
const parsed = JSON.parse(raw);
|
|
@@ -11875,7 +12622,7 @@ var RecallIntrospectionCoordinator = class {
|
|
|
11875
12622
|
}
|
|
11876
12623
|
async getLastQmdRecallSnapshot(namespace) {
|
|
11877
12624
|
const storage = await this.deps.getStorage(namespace);
|
|
11878
|
-
const snapshotPath =
|
|
12625
|
+
const snapshotPath = path13.join(
|
|
11879
12626
|
storage.dir,
|
|
11880
12627
|
"state",
|
|
11881
12628
|
"last_qmd_recall.json"
|
|
@@ -11938,7 +12685,9 @@ var RecallIntrospectionCoordinator = class {
|
|
|
11938
12685
|
`Expanded paths (${snapshot.expandedCount}, showing ${expanded.length}):`,
|
|
11939
12686
|
...expanded.map((e) => {
|
|
11940
12687
|
const confLabel = typeof e.edgeConfidence === "number" && Number.isFinite(e.edgeConfidence) ? e.edgeConfidence.toFixed(2) : "n/a";
|
|
11941
|
-
|
|
12688
|
+
const pathLabel = Array.isArray(e.pathNodeIds) && e.pathNodeIds.length > 0 ? `, path=${e.pathNodeIds.join("->")}` : "";
|
|
12689
|
+
const penaltyLabel = typeof e.pathPenaltyApplied === "boolean" ? `, penalty=${e.pathPenaltyApplied ? "yes" : "no"}` : "";
|
|
12690
|
+
return `- ${e.path} (score=${e.score.toFixed(3)}, ns=${e.namespace}, seed=${e.seed || "unknown"}, hop=${e.hopDepth}, w=${e.decayedWeight.toFixed(3)}, type=${e.graphType}, conf=${confLabel}${penaltyLabel}${pathLabel})`;
|
|
11942
12691
|
}),
|
|
11943
12692
|
`Final ranked results (${snapshot.finalResults?.length ?? 0}, showing ${finalResults.length}):`,
|
|
11944
12693
|
...finalResults.map(
|
|
@@ -12165,12 +12914,12 @@ var RecallIntrospectionCoordinator = class {
|
|
|
12165
12914
|
}
|
|
12166
12915
|
async recordLastIntentSnapshot(options) {
|
|
12167
12916
|
try {
|
|
12168
|
-
const snapshotPath =
|
|
12917
|
+
const snapshotPath = path13.join(
|
|
12169
12918
|
options.storage.dir,
|
|
12170
12919
|
"state",
|
|
12171
12920
|
"last_intent.json"
|
|
12172
12921
|
);
|
|
12173
|
-
await mkdir5(
|
|
12922
|
+
await mkdir5(path13.dirname(snapshotPath), { recursive: true });
|
|
12174
12923
|
await writeFile5(
|
|
12175
12924
|
snapshotPath,
|
|
12176
12925
|
JSON.stringify(options.snapshot, null, 2),
|
|
@@ -12182,12 +12931,12 @@ var RecallIntrospectionCoordinator = class {
|
|
|
12182
12931
|
}
|
|
12183
12932
|
async recordLastQmdRecallSnapshot(options) {
|
|
12184
12933
|
try {
|
|
12185
|
-
const snapshotPath =
|
|
12934
|
+
const snapshotPath = path13.join(
|
|
12186
12935
|
options.storage.dir,
|
|
12187
12936
|
"state",
|
|
12188
12937
|
"last_qmd_recall.json"
|
|
12189
12938
|
);
|
|
12190
|
-
await mkdir5(
|
|
12939
|
+
await mkdir5(path13.dirname(snapshotPath), { recursive: true });
|
|
12191
12940
|
await writeFile5(
|
|
12192
12941
|
snapshotPath,
|
|
12193
12942
|
JSON.stringify(options.snapshot, null, 2),
|
|
@@ -12202,8 +12951,8 @@ var RecallIntrospectionCoordinator = class {
|
|
|
12202
12951
|
const stateDir = await this.deps.resolveStateDirForNamespace(
|
|
12203
12952
|
options.namespace
|
|
12204
12953
|
);
|
|
12205
|
-
const snapshotPath =
|
|
12206
|
-
await mkdir5(
|
|
12954
|
+
const snapshotPath = path13.join(stateDir, "last_intent.json");
|
|
12955
|
+
await mkdir5(path13.dirname(snapshotPath), { recursive: true });
|
|
12207
12956
|
await writeFile5(
|
|
12208
12957
|
snapshotPath,
|
|
12209
12958
|
JSON.stringify(options.snapshot, null, 2),
|
|
@@ -12217,7 +12966,7 @@ var RecallIntrospectionCoordinator = class {
|
|
|
12217
12966
|
|
|
12218
12967
|
// src/orchestration/orchestrator-init.ts
|
|
12219
12968
|
import { readdir as readdir2, stat as stat2, unlink as unlink2 } from "fs/promises";
|
|
12220
|
-
import
|
|
12969
|
+
import path14 from "path";
|
|
12221
12970
|
var OrchestratorInitCoordinator = class {
|
|
12222
12971
|
constructor(deps) {
|
|
12223
12972
|
this.deps = deps;
|
|
@@ -12321,7 +13070,7 @@ var OrchestratorInitCoordinator = class {
|
|
|
12321
13070
|
const files = await readdir2(wsDir).catch(() => []);
|
|
12322
13071
|
for (const f of files) {
|
|
12323
13072
|
if (!f.startsWith(".compaction-reset-signal-")) continue;
|
|
12324
|
-
const fp =
|
|
13073
|
+
const fp = path14.join(wsDir, f);
|
|
12325
13074
|
const s = await stat2(fp).catch(() => null);
|
|
12326
13075
|
if (s && Date.now() - s.mtimeMs >= COMPACTION_SIGNAL_MAX_AGE_MS) {
|
|
12327
13076
|
await unlink2(fp).catch(() => {
|
|
@@ -12673,7 +13422,7 @@ var OrchestratorInitCoordinator = class {
|
|
|
12673
13422
|
};
|
|
12674
13423
|
|
|
12675
13424
|
// src/orchestration/persistence-index.ts
|
|
12676
|
-
import
|
|
13425
|
+
import path15 from "path";
|
|
12677
13426
|
var PersistenceIndexCoordinator = class {
|
|
12678
13427
|
constructor(deps) {
|
|
12679
13428
|
this.deps = deps;
|
|
@@ -12859,7 +13608,7 @@ var PersistenceIndexCoordinator = class {
|
|
|
12859
13608
|
const allMems = allMemsForGraph ?? [];
|
|
12860
13609
|
for (const m of allMems) {
|
|
12861
13610
|
if (m.frontmatter.entityRef === entityRef) {
|
|
12862
|
-
const rel =
|
|
13611
|
+
const rel = path15.relative(storage.dir, m.path);
|
|
12863
13612
|
if (rel !== memoryRelPath) entitySiblings.push(rel);
|
|
12864
13613
|
}
|
|
12865
13614
|
}
|
|
@@ -13007,8 +13756,8 @@ var PersistenceIndexCoordinator = class {
|
|
|
13007
13756
|
};
|
|
13008
13757
|
|
|
13009
13758
|
// src/orchestration/workspace-ops.ts
|
|
13010
|
-
import { lstat, mkdir as mkdir6, readFile as readFile5, readdir as readdir3, realpath, writeFile as writeFile6 } from "fs/promises";
|
|
13011
|
-
import
|
|
13759
|
+
import { lstat as lstat2, mkdir as mkdir6, readFile as readFile5, readdir as readdir3, realpath as realpath2, writeFile as writeFile6 } from "fs/promises";
|
|
13760
|
+
import path16 from "path";
|
|
13012
13761
|
|
|
13013
13762
|
// src/maintenance/pattern-reinforcement.ts
|
|
13014
13763
|
function patternReinforcementKey(content) {
|
|
@@ -14915,8 +15664,8 @@ var MeetingsService = class {
|
|
|
14915
15664
|
// src/orchestration/workspace-ops.ts
|
|
14916
15665
|
var MEETINGS_BUILD_DEBOUNCE_MS = 5e3;
|
|
14917
15666
|
function matchesMemoryPath(candidatePath, requestedPath, memoryDir) {
|
|
14918
|
-
const normalizedCandidate =
|
|
14919
|
-
return normalizedCandidate ===
|
|
15667
|
+
const normalizedCandidate = path16.resolve(candidatePath);
|
|
15668
|
+
return normalizedCandidate === path16.resolve(requestedPath) || normalizedCandidate === path16.resolve(memoryDir, requestedPath);
|
|
14920
15669
|
}
|
|
14921
15670
|
function accessTrackingPathCandidates(storageDir, memoryPath) {
|
|
14922
15671
|
const candidates = qmdResultPathCandidates(storageDir, memoryPath);
|
|
@@ -14924,12 +15673,12 @@ function accessTrackingPathCandidates(storageDir, memoryPath) {
|
|
|
14924
15673
|
if (!parts) return candidates;
|
|
14925
15674
|
candidates.push(
|
|
14926
15675
|
...qmdResultPathCandidates(storageDir, parts.relativePath),
|
|
14927
|
-
...qmdResultPathCandidates(
|
|
15676
|
+
...qmdResultPathCandidates(path16.join(storageDir, "cold"), parts.relativePath)
|
|
14928
15677
|
);
|
|
14929
15678
|
return [...new Set(candidates)];
|
|
14930
15679
|
}
|
|
14931
15680
|
function canonicalMemoryPath(memoryPath, memoryDir) {
|
|
14932
|
-
return
|
|
15681
|
+
return path16.resolve(path16.isAbsolute(memoryPath) ? memoryPath : path16.resolve(memoryDir, memoryPath));
|
|
14933
15682
|
}
|
|
14934
15683
|
var WorkspaceOpsCoordinator = class {
|
|
14935
15684
|
constructor(deps) {
|
|
@@ -15011,15 +15760,15 @@ var WorkspaceOpsCoordinator = class {
|
|
|
15011
15760
|
this.deps.lastFileHygieneRunAtMs = now;
|
|
15012
15761
|
if (hygiene.rotateEnabled) {
|
|
15013
15762
|
for (const rel of hygiene.rotatePaths) {
|
|
15014
|
-
const abs =
|
|
15763
|
+
const abs = path16.isAbsolute(rel) ? rel : path16.join(this.deps.config.workspaceDir, rel);
|
|
15015
15764
|
try {
|
|
15016
15765
|
const raw = await readFile5(abs, "utf-8");
|
|
15017
15766
|
if (raw.length > hygiene.rotateMaxBytes) {
|
|
15018
|
-
const archiveDir =
|
|
15767
|
+
const archiveDir = path16.join(
|
|
15019
15768
|
this.deps.config.workspaceDir,
|
|
15020
15769
|
hygiene.archiveDir
|
|
15021
15770
|
);
|
|
15022
|
-
const base =
|
|
15771
|
+
const base = path16.basename(abs);
|
|
15023
15772
|
const prefix = base.toUpperCase().replace(/\.MD$/i, "").replace(/[^A-Z0-9]+/g, "-") || "FILE";
|
|
15024
15773
|
const { newContent } = await rotateMarkdownFileToArchive({
|
|
15025
15774
|
filePath: abs,
|
|
@@ -15044,8 +15793,8 @@ var WorkspaceOpsCoordinator = class {
|
|
|
15044
15793
|
log.warn(w.message);
|
|
15045
15794
|
}
|
|
15046
15795
|
if (hygiene.warningsLogEnabled && warnings.length > 0) {
|
|
15047
|
-
const fp =
|
|
15048
|
-
await mkdir6(
|
|
15796
|
+
const fp = path16.join(this.deps.config.memoryDir, hygiene.warningsLogPath);
|
|
15797
|
+
await mkdir6(path16.dirname(fp), { recursive: true });
|
|
15049
15798
|
const stamp = (/* @__PURE__ */ new Date()).toISOString();
|
|
15050
15799
|
const block = `
|
|
15051
15800
|
|
|
@@ -15078,25 +15827,25 @@ var WorkspaceOpsCoordinator = class {
|
|
|
15078
15827
|
const facts = [];
|
|
15079
15828
|
let memoryRootReal = null;
|
|
15080
15829
|
try {
|
|
15081
|
-
memoryRootReal = await
|
|
15830
|
+
memoryRootReal = await realpath2(storage.dir);
|
|
15082
15831
|
} catch {
|
|
15083
15832
|
memoryRootReal = null;
|
|
15084
15833
|
}
|
|
15085
15834
|
for (const categoryDir of RECALL_FALLBACK_DIRS) {
|
|
15086
15835
|
if (memoryRootReal === null) break;
|
|
15087
15836
|
for (const date of datesToScan) {
|
|
15088
|
-
const dateDir =
|
|
15837
|
+
const dateDir = path16.join(storage.dir, categoryDir, date);
|
|
15089
15838
|
try {
|
|
15090
|
-
const dirStat = await
|
|
15839
|
+
const dirStat = await lstat2(dateDir);
|
|
15091
15840
|
if (dirStat.isSymbolicLink() || !dirStat.isDirectory()) continue;
|
|
15092
|
-
assertPathInsideRoot(memoryRootReal, await
|
|
15841
|
+
assertPathInsideRoot(memoryRootReal, await realpath2(dateDir), dateDir);
|
|
15093
15842
|
const entries = await readdir3(dateDir, { withFileTypes: true });
|
|
15094
15843
|
for (const entry of entries) {
|
|
15095
15844
|
if (entry.isSymbolicLink()) continue;
|
|
15096
15845
|
if (!entry.name.endsWith(".md")) continue;
|
|
15097
|
-
const fullPath =
|
|
15846
|
+
const fullPath = path16.join(dateDir, entry.name);
|
|
15098
15847
|
try {
|
|
15099
|
-
assertPathInsideRoot(memoryRootReal, await
|
|
15848
|
+
assertPathInsideRoot(memoryRootReal, await realpath2(fullPath), fullPath);
|
|
15100
15849
|
const raw = await readFile5(fullPath, "utf-8");
|
|
15101
15850
|
const fmMatch = raw.match(/^---\n([\s\S]*?)\n---\n?([\s\S]*)$/);
|
|
15102
15851
|
if (!fmMatch) continue;
|
|
@@ -15116,7 +15865,7 @@ var WorkspaceOpsCoordinator = class {
|
|
|
15116
15865
|
facts.push({
|
|
15117
15866
|
path: fullPath,
|
|
15118
15867
|
frontmatter: {
|
|
15119
|
-
id: fm.id ||
|
|
15868
|
+
id: fm.id || path16.basename(entry.name, ".md"),
|
|
15120
15869
|
category: fm.category || "fact",
|
|
15121
15870
|
created,
|
|
15122
15871
|
updated: fm.updated || created,
|
|
@@ -15139,13 +15888,13 @@ var WorkspaceOpsCoordinator = class {
|
|
|
15139
15888
|
return a.frontmatter.created < b.frontmatter.created ? -1 : 1;
|
|
15140
15889
|
});
|
|
15141
15890
|
const hourlySummaries = [];
|
|
15142
|
-
const hourlyBaseDir =
|
|
15891
|
+
const hourlyBaseDir = path16.join(storage.dir, "summaries", "hourly");
|
|
15143
15892
|
try {
|
|
15144
15893
|
const sessionKeys = await readdir3(hourlyBaseDir, { withFileTypes: true });
|
|
15145
15894
|
for (const sk of sessionKeys) {
|
|
15146
15895
|
if (!sk.isDirectory()) continue;
|
|
15147
15896
|
for (const date of datesToScan) {
|
|
15148
|
-
const summaryFile =
|
|
15897
|
+
const summaryFile = path16.join(hourlyBaseDir, sk.name, `${date}.md`);
|
|
15149
15898
|
try {
|
|
15150
15899
|
const raw = await readFile5(summaryFile, "utf-8");
|
|
15151
15900
|
const filtered = filterHourlySummaryMarkdownForLocalDay(
|
|
@@ -15609,18 +16358,18 @@ ${reflectionsContent.trim()}
|
|
|
15609
16358
|
// src/orchestration/namespace-read-fanout.ts
|
|
15610
16359
|
import { existsSync, readFileSync } from "fs";
|
|
15611
16360
|
import { stat as stat3 } from "fs/promises";
|
|
15612
|
-
import
|
|
16361
|
+
import path18 from "path";
|
|
15613
16362
|
|
|
15614
16363
|
// src/orchestration/orchestrator-namespace-scope.ts
|
|
15615
|
-
import
|
|
16364
|
+
import path17 from "path";
|
|
15616
16365
|
function computeSemanticDedupScope(targetStorage, config) {
|
|
15617
16366
|
if (!resolveNamespaceCapabilities(config).namespaces) return {};
|
|
15618
|
-
const memoryDir =
|
|
15619
|
-
const storageDir =
|
|
16367
|
+
const memoryDir = path17.resolve(config.memoryDir);
|
|
16368
|
+
const storageDir = path17.resolve(targetStorage.dir);
|
|
15620
16369
|
if (storageDir === memoryDir) {
|
|
15621
16370
|
return { pathExcludePrefixes: ["namespaces/"] };
|
|
15622
16371
|
}
|
|
15623
|
-
let rel =
|
|
16372
|
+
let rel = path17.relative(memoryDir, storageDir);
|
|
15624
16373
|
if (!rel || rel.startsWith("..")) {
|
|
15625
16374
|
log.debug(
|
|
15626
16375
|
`semantic dedup: target storage dir ${storageDir} is outside memoryDir ${memoryDir}; scoping lookup to absolute path prefix`
|
|
@@ -15673,7 +16422,7 @@ var NamespaceReadFanoutCoordinator = class {
|
|
|
15673
16422
|
loadNamespaceStorageDirHintsFromCatalog() {
|
|
15674
16423
|
if (this.deps.namespaceStorageDirHintsLoaded || !this.deps.namespaceCatalog.enabled) return;
|
|
15675
16424
|
this.deps.namespaceStorageDirHintsLoaded = true;
|
|
15676
|
-
const catalogPath =
|
|
16425
|
+
const catalogPath = path18.join(this.deps.config.memoryDir, "state", "namespaces.jsonl");
|
|
15677
16426
|
if (!existsSync(catalogPath)) return;
|
|
15678
16427
|
let body;
|
|
15679
16428
|
try {
|
|
@@ -15710,7 +16459,7 @@ var NamespaceReadFanoutCoordinator = class {
|
|
|
15710
16459
|
if (!this.deps.storageDirMatchesNamespaceHint(record.namespace, record.storageDir)) {
|
|
15711
16460
|
continue;
|
|
15712
16461
|
}
|
|
15713
|
-
const resolvedStorageDir =
|
|
16462
|
+
const resolvedStorageDir = path18.resolve(record.storageDir);
|
|
15714
16463
|
const current = preferredByStorageDir.get(resolvedStorageDir);
|
|
15715
16464
|
preferredByStorageDir.set(
|
|
15716
16465
|
resolvedStorageDir,
|
|
@@ -15894,12 +16643,12 @@ var NamespaceReadFanoutCoordinator = class {
|
|
|
15894
16643
|
}
|
|
15895
16644
|
async resolveStateDirForNamespace(namespace) {
|
|
15896
16645
|
if (!resolveNamespaceCapabilities(this.deps.config).namespaces) {
|
|
15897
|
-
return
|
|
16646
|
+
return path18.join(this.deps.config.memoryDir, "state");
|
|
15898
16647
|
}
|
|
15899
16648
|
if (namespace !== this.deps.config.defaultNamespace) {
|
|
15900
|
-
return
|
|
16649
|
+
return path18.join(this.deps.config.memoryDir, "namespaces", namespace, "state");
|
|
15901
16650
|
}
|
|
15902
|
-
const candidate =
|
|
16651
|
+
const candidate = path18.join(
|
|
15903
16652
|
this.deps.config.memoryDir,
|
|
15904
16653
|
"namespaces",
|
|
15905
16654
|
this.deps.config.defaultNamespace
|
|
@@ -15907,11 +16656,11 @@ var NamespaceReadFanoutCoordinator = class {
|
|
|
15907
16656
|
try {
|
|
15908
16657
|
const candidateStat = await stat3(candidate);
|
|
15909
16658
|
if (candidateStat.isDirectory()) {
|
|
15910
|
-
return
|
|
16659
|
+
return path18.join(candidate, "state");
|
|
15911
16660
|
}
|
|
15912
16661
|
} catch {
|
|
15913
16662
|
}
|
|
15914
|
-
return
|
|
16663
|
+
return path18.join(this.deps.config.memoryDir, "state");
|
|
15915
16664
|
}
|
|
15916
16665
|
namespaceFromPath(p) {
|
|
15917
16666
|
if (!resolveNamespaceCapabilities(this.deps.config).namespaces) return this.deps.config.defaultNamespace;
|
|
@@ -16461,7 +17210,7 @@ var Orchestrator = class {
|
|
|
16461
17210
|
loadRoutingRules: () => this.loadRoutingRules(),
|
|
16462
17211
|
routeEngineOptions: () => this.routeEngineOptions(),
|
|
16463
17212
|
semanticDedupLookup: (content, limit, targetStorage) => this.semanticDedupLookup(content, limit, targetStorage),
|
|
16464
|
-
checkForContradiction: (content, category, namespaceScope) => this.checkForContradiction(content, category, namespaceScope),
|
|
17213
|
+
checkForContradiction: (content, category, namespaceScope, anchor) => this.checkForContradiction(content, category, namespaceScope, anchor),
|
|
16465
17214
|
applyDeferredContradictionResolve: (contradiction, storage, newMemoryId, postWriteGuard) => this.applyDeferredContradictionResolve(contradiction, storage, newMemoryId, postWriteGuard),
|
|
16466
17215
|
suggestLinksForMemory: (content, category, namespaceScope) => this.suggestLinksForMemory(content, category, namespaceScope),
|
|
16467
17216
|
storageDirNamespace: (storageDir) => this.storageDirNamespace(storageDir),
|
|
@@ -16692,7 +17441,7 @@ var Orchestrator = class {
|
|
|
16692
17441
|
const defaultNs = normalizeNamespaceIdentity(this.config.defaultNamespace);
|
|
16693
17442
|
if (ns !== defaultNs && !isSafeRouteNamespace(ns)) return;
|
|
16694
17443
|
if (!this.storageDirMatchesNamespaceHint(ns, storageDir)) return;
|
|
16695
|
-
const resolvedStorageDir =
|
|
17444
|
+
const resolvedStorageDir = path19.resolve(storageDir);
|
|
16696
17445
|
let hints = this.namespaceStorageDirHints.get(resolvedStorageDir);
|
|
16697
17446
|
if (!hints) {
|
|
16698
17447
|
hints = /* @__PURE__ */ new Set();
|
|
@@ -16703,21 +17452,21 @@ var Orchestrator = class {
|
|
|
16703
17452
|
storageDirMatchesNamespaceHint(namespace, storageDir) {
|
|
16704
17453
|
const ns = normalizeNamespaceIdentity(namespace);
|
|
16705
17454
|
if (!ns) return false;
|
|
16706
|
-
const resolvedStorageDir =
|
|
16707
|
-
const resolvedMemoryDir =
|
|
17455
|
+
const resolvedStorageDir = path19.resolve(storageDir);
|
|
17456
|
+
const resolvedMemoryDir = path19.resolve(this.config.memoryDir);
|
|
16708
17457
|
const defaultNs = normalizeNamespaceIdentity(this.config.defaultNamespace);
|
|
16709
17458
|
if (resolvedStorageDir === resolvedMemoryDir) return ns === defaultNs;
|
|
16710
|
-
const resolvedNamespacesDir =
|
|
17459
|
+
const resolvedNamespacesDir = path19.join(resolvedMemoryDir, "namespaces");
|
|
16711
17460
|
if (!isPathInsideStorageRoot(resolvedNamespacesDir, resolvedStorageDir)) return false;
|
|
16712
|
-
const rawRoot =
|
|
16713
|
-
const tokenRoot =
|
|
17461
|
+
const rawRoot = path19.resolve(resolvedNamespacesDir, ns);
|
|
17462
|
+
const tokenRoot = path19.resolve(resolvedNamespacesDir, namespaceIdentityToken(ns));
|
|
16714
17463
|
return resolvedStorageDir === rawRoot || resolvedStorageDir === tokenRoot;
|
|
16715
17464
|
}
|
|
16716
17465
|
namespaceStorageDirHintOwnershipRank(record, resolvedStorageDir, configured) {
|
|
16717
|
-
if (resolvedStorageDir ===
|
|
17466
|
+
if (resolvedStorageDir === path19.resolve(this.config.memoryDir)) {
|
|
16718
17467
|
return record.namespace === normalizeNamespaceIdentity(this.config.defaultNamespace) ? 0 : 3;
|
|
16719
17468
|
}
|
|
16720
|
-
const leaf =
|
|
17469
|
+
const leaf = path19.basename(resolvedStorageDir);
|
|
16721
17470
|
const tokenOwnsRoot = namespaceIdentityToken(record.namespace) === leaf;
|
|
16722
17471
|
if (tokenOwnsRoot && configured.has(record.namespace)) return 0;
|
|
16723
17472
|
if (record.namespace === leaf) return 1;
|
|
@@ -16857,7 +17606,7 @@ var Orchestrator = class {
|
|
|
16857
17606
|
StorageManager.setScopedCacheInvalidationDefault(config.memoryDir, scopedCacheInvalidationEnabled);
|
|
16858
17607
|
this.profiler = new ProfilingCollector({
|
|
16859
17608
|
enabled: resolvePipelineProcessingCapabilities(this.config).profiling,
|
|
16860
|
-
storageDir: config.profilingStorageDir ||
|
|
17609
|
+
storageDir: config.profilingStorageDir || path19.join(config.memoryDir, "profiling"),
|
|
16861
17610
|
maxTraces: config.profilingMaxTraces
|
|
16862
17611
|
});
|
|
16863
17612
|
this.namespaceCatalog = new NamespaceCatalog(config);
|
|
@@ -16944,7 +17693,7 @@ var Orchestrator = class {
|
|
|
16944
17693
|
this.compounding = resolveConsolidationCapabilities(config).compounding ? new CompoundingEngine(config, this.storage) : void 0;
|
|
16945
17694
|
this.buffer = new SmartBuffer(config, this.storage);
|
|
16946
17695
|
this.transcript = new TranscriptManager(config);
|
|
16947
|
-
this.conversationIndexDir =
|
|
17696
|
+
this.conversationIndexDir = path19.join(
|
|
16948
17697
|
config.memoryDir,
|
|
16949
17698
|
"conversation-index",
|
|
16950
17699
|
"chunks"
|
|
@@ -17092,7 +17841,7 @@ var Orchestrator = class {
|
|
|
17092
17841
|
saveContentHashIndexes: () => this.saveContentHashIndexes()
|
|
17093
17842
|
});
|
|
17094
17843
|
this.threading = new ThreadingManager(
|
|
17095
|
-
|
|
17844
|
+
path19.join(config.memoryDir, "threads"),
|
|
17096
17845
|
config.threadingGapMinutes
|
|
17097
17846
|
);
|
|
17098
17847
|
const lifecycleCaps = resolveMemoryLifecycleCapabilities(config);
|
|
@@ -17655,8 +18404,8 @@ ${doc.content}` : doc.content,
|
|
|
17655
18404
|
);
|
|
17656
18405
|
}
|
|
17657
18406
|
// Issue #1526 (seam 14): graph-recall expansion moved to
|
|
17658
|
-
// GraphRecallCoordinator.
|
|
17659
|
-
//
|
|
18407
|
+
// GraphRecallCoordinator. Keep this public seam so callers and tests can
|
|
18408
|
+
// override graph expansion on the orchestrator instance.
|
|
17660
18409
|
async expandResultsViaGraph(options) {
|
|
17661
18410
|
return this.graphRecallCoordinator.expandResultsViaGraph(options);
|
|
17662
18411
|
}
|
|
@@ -18383,11 +19132,12 @@ ${doc.content}` : doc.content,
|
|
|
18383
19132
|
* Check if a new memory contradicts an existing one.
|
|
18384
19133
|
* Uses QMD to find similar memories, then LLM to verify contradiction.
|
|
18385
19134
|
*/
|
|
18386
|
-
async checkForContradiction(content, category, namespaceScope) {
|
|
19135
|
+
async checkForContradiction(content, category, namespaceScope, anchor) {
|
|
18387
19136
|
return this.contradictionLinkingCoordinator.checkForContradiction(
|
|
18388
19137
|
content,
|
|
18389
19138
|
category,
|
|
18390
|
-
namespaceScope
|
|
19139
|
+
namespaceScope,
|
|
19140
|
+
anchor
|
|
18391
19141
|
);
|
|
18392
19142
|
}
|
|
18393
19143
|
/**
|
|
@@ -19195,9 +19945,9 @@ function readStructuralSymbol(entry) {
|
|
|
19195
19945
|
const rec = entry;
|
|
19196
19946
|
const symbol = typeof rec.symbol === "string" ? rec.symbol.trim() : "";
|
|
19197
19947
|
if (!symbol) return null;
|
|
19198
|
-
const
|
|
19948
|
+
const path34 = typeof rec.path === "string" && rec.path.length > 0 ? rec.path : void 0;
|
|
19199
19949
|
const kind = typeof rec.kind === "string" && rec.kind.length > 0 ? rec.kind : void 0;
|
|
19200
|
-
const item =
|
|
19950
|
+
const item = path34 !== void 0 && kind !== void 0 ? { symbol, path: path34, kind } : path34 !== void 0 ? { symbol, path: path34 } : kind !== void 0 ? { symbol, kind } : { symbol };
|
|
19201
19951
|
return item;
|
|
19202
19952
|
}
|
|
19203
19953
|
function classifySpawnError(err) {
|
|
@@ -19271,7 +20021,7 @@ var DEFAULT_GRACE_PERIOD_DAYS = 7;
|
|
|
19271
20021
|
|
|
19272
20022
|
// src/binary-lifecycle/backend.ts
|
|
19273
20023
|
import fsp from "fs/promises";
|
|
19274
|
-
import
|
|
20024
|
+
import path20 from "path";
|
|
19275
20025
|
var FilesystemBackend = class {
|
|
19276
20026
|
type = "filesystem";
|
|
19277
20027
|
basePath;
|
|
@@ -19279,19 +20029,19 @@ var FilesystemBackend = class {
|
|
|
19279
20029
|
if (!basePath || basePath.trim().length === 0) {
|
|
19280
20030
|
throw new Error("FilesystemBackend requires a non-empty basePath");
|
|
19281
20031
|
}
|
|
19282
|
-
this.basePath =
|
|
20032
|
+
this.basePath = path20.resolve(basePath);
|
|
19283
20033
|
}
|
|
19284
20034
|
resolveRemotePath(remotePath) {
|
|
19285
|
-
const resolved =
|
|
19286
|
-
const relative =
|
|
19287
|
-
if (relative === ".." || relative.startsWith(`..${
|
|
20035
|
+
const resolved = path20.isAbsolute(remotePath) ? path20.resolve(remotePath) : path20.resolve(this.basePath, remotePath);
|
|
20036
|
+
const relative = path20.relative(this.basePath, resolved);
|
|
20037
|
+
if (relative === ".." || relative.startsWith(`..${path20.sep}`) || path20.isAbsolute(relative)) {
|
|
19288
20038
|
throw new Error(`FilesystemBackend remotePath escapes basePath: ${JSON.stringify(remotePath)}`);
|
|
19289
20039
|
}
|
|
19290
20040
|
return resolved;
|
|
19291
20041
|
}
|
|
19292
20042
|
isInsideBase(candidate, realBase) {
|
|
19293
|
-
const relative =
|
|
19294
|
-
return relative === "" || relative !== ".." && !relative.startsWith(`..${
|
|
20043
|
+
const relative = path20.relative(realBase, candidate);
|
|
20044
|
+
return relative === "" || relative !== ".." && !relative.startsWith(`..${path20.sep}`) && !path20.isAbsolute(relative);
|
|
19295
20045
|
}
|
|
19296
20046
|
async realBasePathIfExists() {
|
|
19297
20047
|
try {
|
|
@@ -19320,13 +20070,13 @@ var FilesystemBackend = class {
|
|
|
19320
20070
|
}
|
|
19321
20071
|
async ensureSafeParentDirectory(dest) {
|
|
19322
20072
|
const realBase = await this.ensureBaseDirectory();
|
|
19323
|
-
const destDir =
|
|
19324
|
-
const relativeDir =
|
|
19325
|
-
const segments = relativeDir === "" ? [] : relativeDir.split(
|
|
20073
|
+
const destDir = path20.dirname(dest);
|
|
20074
|
+
const relativeDir = path20.relative(this.basePath, destDir);
|
|
20075
|
+
const segments = relativeDir === "" ? [] : relativeDir.split(path20.sep);
|
|
19326
20076
|
let current = this.basePath;
|
|
19327
20077
|
for (const segment of segments) {
|
|
19328
20078
|
if (segment === "." || segment === "") continue;
|
|
19329
|
-
current =
|
|
20079
|
+
current = path20.join(current, segment);
|
|
19330
20080
|
try {
|
|
19331
20081
|
const stat5 = await fsp.lstat(current);
|
|
19332
20082
|
if (stat5.isSymbolicLink()) {
|
|
@@ -19354,13 +20104,13 @@ var FilesystemBackend = class {
|
|
|
19354
20104
|
if (realBase === null) {
|
|
19355
20105
|
return null;
|
|
19356
20106
|
}
|
|
19357
|
-
const destDir =
|
|
19358
|
-
const relativeDir =
|
|
19359
|
-
const segments = relativeDir === "" ? [] : relativeDir.split(
|
|
20107
|
+
const destDir = path20.dirname(dest);
|
|
20108
|
+
const relativeDir = path20.relative(this.basePath, destDir);
|
|
20109
|
+
const segments = relativeDir === "" ? [] : relativeDir.split(path20.sep);
|
|
19360
20110
|
let current = this.basePath;
|
|
19361
20111
|
for (const segment of segments) {
|
|
19362
20112
|
if (segment === "." || segment === "") continue;
|
|
19363
|
-
current =
|
|
20113
|
+
current = path20.join(current, segment);
|
|
19364
20114
|
let stat5;
|
|
19365
20115
|
try {
|
|
19366
20116
|
stat5 = await fsp.lstat(current);
|
|
@@ -19408,7 +20158,7 @@ var FilesystemBackend = class {
|
|
|
19408
20158
|
return dest;
|
|
19409
20159
|
}
|
|
19410
20160
|
async upload(localPath, remotePath) {
|
|
19411
|
-
if (
|
|
20161
|
+
if (path20.isAbsolute(remotePath)) {
|
|
19412
20162
|
throw new Error(`FilesystemBackend upload remotePath must be relative: ${JSON.stringify(remotePath)}`);
|
|
19413
20163
|
}
|
|
19414
20164
|
const dest = this.resolveRemotePath(remotePath);
|
|
@@ -19481,7 +20231,7 @@ function createBackend(cfg) {
|
|
|
19481
20231
|
|
|
19482
20232
|
// src/binary-lifecycle/scanner.ts
|
|
19483
20233
|
import fsp2 from "fs/promises";
|
|
19484
|
-
import
|
|
20234
|
+
import path21 from "path";
|
|
19485
20235
|
import crypto from "crypto";
|
|
19486
20236
|
function matchesPatterns(filename, patterns) {
|
|
19487
20237
|
const lower = filename.toLowerCase();
|
|
@@ -19506,8 +20256,8 @@ async function scanForBinaries(memoryDir, config, manifest) {
|
|
|
19506
20256
|
return;
|
|
19507
20257
|
}
|
|
19508
20258
|
for (const entry of entries) {
|
|
19509
|
-
const fullPath =
|
|
19510
|
-
const relativePath =
|
|
20259
|
+
const fullPath = path21.join(dir, entry.name);
|
|
20260
|
+
const relativePath = path21.relative(memoryDir, fullPath).split(path21.sep).join("/");
|
|
19511
20261
|
if (entry.isDirectory()) {
|
|
19512
20262
|
if (entry.name === ".binary-lifecycle") continue;
|
|
19513
20263
|
await walk(fullPath);
|
|
@@ -19547,15 +20297,15 @@ async function hashFile(filePath) {
|
|
|
19547
20297
|
|
|
19548
20298
|
// src/binary-lifecycle/manifest.ts
|
|
19549
20299
|
import fsp3 from "fs/promises";
|
|
19550
|
-
import
|
|
20300
|
+
import path22 from "path";
|
|
19551
20301
|
import crypto2 from "crypto";
|
|
19552
20302
|
var MANIFEST_DIR = ".binary-lifecycle";
|
|
19553
20303
|
var MANIFEST_FILE = "manifest.json";
|
|
19554
20304
|
function manifestDir(memoryDir) {
|
|
19555
|
-
return
|
|
20305
|
+
return path22.join(memoryDir, MANIFEST_DIR);
|
|
19556
20306
|
}
|
|
19557
20307
|
function manifestPath(memoryDir) {
|
|
19558
|
-
return
|
|
20308
|
+
return path22.join(memoryDir, MANIFEST_DIR, MANIFEST_FILE);
|
|
19559
20309
|
}
|
|
19560
20310
|
async function readManifest(memoryDir) {
|
|
19561
20311
|
const filePath = manifestPath(memoryDir);
|
|
@@ -19607,13 +20357,13 @@ function emptyManifest() {
|
|
|
19607
20357
|
|
|
19608
20358
|
// src/binary-lifecycle/pipeline.ts
|
|
19609
20359
|
import fsp4 from "fs/promises";
|
|
19610
|
-
import
|
|
20360
|
+
import path23 from "path";
|
|
19611
20361
|
import crypto3 from "crypto";
|
|
19612
20362
|
var historicalIdCache = new HistoricalEntityCanonicalIdCache();
|
|
19613
20363
|
function isRecallCorpusMarkdown(mdPath, memoryDir) {
|
|
19614
|
-
const rel =
|
|
19615
|
-
if (rel.startsWith("..") ||
|
|
19616
|
-
const top = rel.split(
|
|
20364
|
+
const rel = path23.relative(memoryDir, mdPath);
|
|
20365
|
+
if (rel.startsWith("..") || path23.isAbsolute(rel)) return false;
|
|
20366
|
+
const top = rel.split(path23.sep)[0];
|
|
19617
20367
|
return RECALL_FALLBACK_DIRS.includes(top);
|
|
19618
20368
|
}
|
|
19619
20369
|
async function hashFile2(filePath) {
|
|
@@ -19637,13 +20387,13 @@ function escapeRegex(s) {
|
|
|
19637
20387
|
return s.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
19638
20388
|
}
|
|
19639
20389
|
function resolveManifestAssetPath(memoryDir, originalPath) {
|
|
19640
|
-
if (originalPath.length === 0 || originalPath.includes("\0") || originalPath.includes("\\") ||
|
|
20390
|
+
if (originalPath.length === 0 || originalPath.includes("\0") || originalPath.includes("\\") || path23.isAbsolute(originalPath) || path23.win32.isAbsolute(originalPath)) {
|
|
19641
20391
|
return null;
|
|
19642
20392
|
}
|
|
19643
|
-
const memoryRoot =
|
|
19644
|
-
const fullPath =
|
|
19645
|
-
const relative =
|
|
19646
|
-
if (relative === "" || relative === ".." || relative.startsWith(`..${
|
|
20393
|
+
const memoryRoot = path23.resolve(memoryDir);
|
|
20394
|
+
const fullPath = path23.resolve(memoryRoot, originalPath);
|
|
20395
|
+
const relative = path23.relative(memoryRoot, fullPath);
|
|
20396
|
+
if (relative === "" || relative === ".." || relative.startsWith(`..${path23.sep}`) || path23.isAbsolute(relative)) {
|
|
19647
20397
|
return null;
|
|
19648
20398
|
}
|
|
19649
20399
|
return fullPath;
|
|
@@ -19654,7 +20404,7 @@ function validateBinaryLifecycleConfig(config) {
|
|
|
19654
20404
|
}
|
|
19655
20405
|
}
|
|
19656
20406
|
function remotePathForAsset(backend, relPath) {
|
|
19657
|
-
const normalized = relPath.split(
|
|
20407
|
+
const normalized = relPath.split(path23.sep).join("/");
|
|
19658
20408
|
if (backend.type === "filesystem") {
|
|
19659
20409
|
return `.binary-lifecycle/mirrors/${normalized}`;
|
|
19660
20410
|
}
|
|
@@ -19667,11 +20417,11 @@ async function stageMirror(memoryDir, newPaths, backend, assets, log2, dryRun) {
|
|
|
19667
20417
|
let mirrored = 0;
|
|
19668
20418
|
const errors = [];
|
|
19669
20419
|
for (const relPath of newPaths) {
|
|
19670
|
-
const fullPath =
|
|
20420
|
+
const fullPath = path23.join(memoryDir, relPath);
|
|
19671
20421
|
try {
|
|
19672
20422
|
const stat5 = await fsp4.stat(fullPath);
|
|
19673
20423
|
const contentHash = await hashFile2(fullPath);
|
|
19674
|
-
const ext =
|
|
20424
|
+
const ext = path23.extname(relPath);
|
|
19675
20425
|
const mimeType = guessMimeType(ext);
|
|
19676
20426
|
const remotePath = remotePathForAsset(backend, relPath);
|
|
19677
20427
|
let backendLocation = remotePath;
|
|
@@ -19809,7 +20559,7 @@ async function stageRedirect(memoryDir, assets, log2, dryRun, readMarkdownFile,
|
|
|
19809
20559
|
for (const update of updates) {
|
|
19810
20560
|
try {
|
|
19811
20561
|
await withRawEntityPageMutation(memoryDir, update.mdPath, async () => {
|
|
19812
|
-
const stateDir =
|
|
20562
|
+
const stateDir = path23.join(memoryDir, "state");
|
|
19813
20563
|
const kind = classifyEntityRefWritePath(memoryDir, update.mdPath);
|
|
19814
20564
|
if (kind === "memory") {
|
|
19815
20565
|
const idsAtWrite = historicalIdCache.get(stateDir);
|
|
@@ -19903,10 +20653,10 @@ async function countRemainingLocalReferences(memoryDir, asset, assetAbsolute, md
|
|
|
19903
20653
|
return { remaining, errors };
|
|
19904
20654
|
}
|
|
19905
20655
|
function markdownReferencePattern(asset, assetAbsolute, mdPath) {
|
|
19906
|
-
const mdDir =
|
|
20656
|
+
const mdDir = path23.dirname(mdPath);
|
|
19907
20657
|
const candidates = /* @__PURE__ */ new Set();
|
|
19908
20658
|
const addCandidate = (candidate) => {
|
|
19909
|
-
const normalized = candidate.split(
|
|
20659
|
+
const normalized = candidate.split(path23.sep).join("/");
|
|
19910
20660
|
if (normalized.length === 0) return;
|
|
19911
20661
|
candidates.add(normalized);
|
|
19912
20662
|
const isParentTraversal = normalized === ".." || normalized.startsWith("../");
|
|
@@ -19914,10 +20664,10 @@ function markdownReferencePattern(asset, assetAbsolute, mdPath) {
|
|
|
19914
20664
|
candidates.add(`./${normalized}`);
|
|
19915
20665
|
}
|
|
19916
20666
|
};
|
|
19917
|
-
addCandidate(
|
|
19918
|
-
const originalPath = asset.originalPath.split(
|
|
19919
|
-
const originalAsFileRelative =
|
|
19920
|
-
if (
|
|
20667
|
+
addCandidate(path23.relative(mdDir, assetAbsolute));
|
|
20668
|
+
const originalPath = asset.originalPath.split(path23.sep).join("/");
|
|
20669
|
+
const originalAsFileRelative = path23.resolve(mdDir, ...originalPath.split("/"));
|
|
20670
|
+
if (path23.resolve(originalAsFileRelative) === path23.resolve(assetAbsolute)) {
|
|
19921
20671
|
addCandidate(originalPath);
|
|
19922
20672
|
}
|
|
19923
20673
|
addCandidate(`/${originalPath}`);
|
|
@@ -20013,7 +20763,7 @@ async function findMarkdownFiles(dir) {
|
|
|
20013
20763
|
return;
|
|
20014
20764
|
}
|
|
20015
20765
|
for (const entry of entries) {
|
|
20016
|
-
const full =
|
|
20766
|
+
const full = path23.join(current, entry.name);
|
|
20017
20767
|
if (entry.isDirectory()) {
|
|
20018
20768
|
if (entry.name === ".binary-lifecycle") continue;
|
|
20019
20769
|
await walk(full);
|
|
@@ -20088,7 +20838,7 @@ async function runBinaryLifecyclePipeline(memoryDir, config, backend, log2, opts
|
|
|
20088
20838
|
|
|
20089
20839
|
// src/projection/index.ts
|
|
20090
20840
|
import fs from "fs";
|
|
20091
|
-
import
|
|
20841
|
+
import path24 from "path";
|
|
20092
20842
|
var VALID_PROJECTION_CATEGORIES = new Set(ALL_CATEGORY_KEYS);
|
|
20093
20843
|
async function generateContextTree(options) {
|
|
20094
20844
|
const startTime = Date.now();
|
|
@@ -20103,8 +20853,8 @@ async function generateContextTree(options) {
|
|
|
20103
20853
|
let nodesGenerated = 0;
|
|
20104
20854
|
let nodesSkipped = 0;
|
|
20105
20855
|
const categoryCounts = {};
|
|
20106
|
-
const resolvedMemoryDir =
|
|
20107
|
-
const resolvedOutputDir =
|
|
20856
|
+
const resolvedMemoryDir = path24.resolve(memoryDir);
|
|
20857
|
+
const resolvedOutputDir = path24.resolve(outputDir);
|
|
20108
20858
|
const requestedCategories = validateProjectionCategories(filterCategories);
|
|
20109
20859
|
const realMemoryDir = assertSafeMemoryRoot(resolvedMemoryDir);
|
|
20110
20860
|
assertNotSymlink(resolvedOutputDir, "context tree outputDir");
|
|
@@ -20142,7 +20892,7 @@ async function generateContextTree(options) {
|
|
|
20142
20892
|
}
|
|
20143
20893
|
}
|
|
20144
20894
|
if (includeEntities) {
|
|
20145
|
-
const entitiesDir =
|
|
20895
|
+
const entitiesDir = path24.join(memoryDir, "entities");
|
|
20146
20896
|
if (fs.existsSync(entitiesDir)) {
|
|
20147
20897
|
assertSafeInputRoot(realMemoryDir, entitiesDir, "entities root");
|
|
20148
20898
|
categoryCounts["entity"] = 0;
|
|
@@ -20154,7 +20904,7 @@ async function generateContextTree(options) {
|
|
|
20154
20904
|
continue;
|
|
20155
20905
|
}
|
|
20156
20906
|
const content = fs.readFileSync(filePath, "utf8");
|
|
20157
|
-
const fileName =
|
|
20907
|
+
const fileName = path24.basename(filePath, ".md");
|
|
20158
20908
|
const node = projectEntityNode(fileName, content);
|
|
20159
20909
|
const outputPath = resolveContainedOutputPath(realOutputDir, "entities", `${fileName}.md`);
|
|
20160
20910
|
writeProjectedContent(realOutputDir, outputPath, node.content);
|
|
@@ -20166,7 +20916,7 @@ async function generateContextTree(options) {
|
|
|
20166
20916
|
}
|
|
20167
20917
|
const shouldIncludeQuestions = includeQuestions && (requestedCategories === void 0 || requestedCategories.includes("question"));
|
|
20168
20918
|
if (shouldIncludeQuestions) {
|
|
20169
|
-
const questionsDir =
|
|
20919
|
+
const questionsDir = path24.join(memoryDir, "questions");
|
|
20170
20920
|
if (fs.existsSync(questionsDir)) {
|
|
20171
20921
|
assertSafeInputRoot(realMemoryDir, questionsDir, "questions root");
|
|
20172
20922
|
categoryCounts["question"] = 0;
|
|
@@ -20207,8 +20957,8 @@ async function generateContextTree(options) {
|
|
|
20207
20957
|
};
|
|
20208
20958
|
}
|
|
20209
20959
|
function isPathInside(root, candidate) {
|
|
20210
|
-
const relative =
|
|
20211
|
-
return relative === "" || !relative.startsWith("..") && !
|
|
20960
|
+
const relative = path24.relative(root, candidate);
|
|
20961
|
+
return relative === "" || !relative.startsWith("..") && !path24.isAbsolute(relative);
|
|
20212
20962
|
}
|
|
20213
20963
|
function assertNotSymlink(targetPath, label) {
|
|
20214
20964
|
try {
|
|
@@ -20245,12 +20995,12 @@ function assertSafeInputRoot(realMemoryDir, targetPath, label) {
|
|
|
20245
20995
|
}
|
|
20246
20996
|
function assertSafeOutputTarget(realOutputDir, outputPath) {
|
|
20247
20997
|
let current = realOutputDir;
|
|
20248
|
-
const relative =
|
|
20249
|
-
if (relative.startsWith("..") ||
|
|
20998
|
+
const relative = path24.relative(realOutputDir, outputPath);
|
|
20999
|
+
if (relative.startsWith("..") || path24.isAbsolute(relative)) {
|
|
20250
21000
|
throw new Error(`context tree output path escapes outputDir: ${outputPath}`);
|
|
20251
21001
|
}
|
|
20252
|
-
for (const segment of relative.split(
|
|
20253
|
-
current =
|
|
21002
|
+
for (const segment of relative.split(path24.sep).filter(Boolean)) {
|
|
21003
|
+
current = path24.join(current, segment);
|
|
20254
21004
|
try {
|
|
20255
21005
|
const stat5 = fs.lstatSync(current);
|
|
20256
21006
|
if (stat5.isSymbolicLink()) {
|
|
@@ -20280,17 +21030,17 @@ function validateProjectionCategories(categories) {
|
|
|
20280
21030
|
return validated;
|
|
20281
21031
|
}
|
|
20282
21032
|
function resolveContainedOutputPath(outputRoot, ...segments) {
|
|
20283
|
-
const resolved =
|
|
20284
|
-
const relative =
|
|
20285
|
-
if (relative === "" || !relative.startsWith("..") && !
|
|
21033
|
+
const resolved = path24.resolve(outputRoot, ...segments);
|
|
21034
|
+
const relative = path24.relative(outputRoot, resolved);
|
|
21035
|
+
if (relative === "" || !relative.startsWith("..") && !path24.isAbsolute(relative)) {
|
|
20286
21036
|
return resolved;
|
|
20287
21037
|
}
|
|
20288
21038
|
throw new Error(`context tree output path escapes outputDir: ${segments.join("/")}`);
|
|
20289
21039
|
}
|
|
20290
21040
|
function writeProjectedContent(realOutputDir, outputPath, generatedContent) {
|
|
20291
21041
|
assertSafeOutputTarget(realOutputDir, outputPath);
|
|
20292
|
-
fs.mkdirSync(
|
|
20293
|
-
const realParent = fs.realpathSync(
|
|
21042
|
+
fs.mkdirSync(path24.dirname(outputPath), { recursive: true });
|
|
21043
|
+
const realParent = fs.realpathSync(path24.dirname(outputPath));
|
|
20294
21044
|
if (!isPathInside(realOutputDir, realParent)) {
|
|
20295
21045
|
throw new Error(`context tree output path escapes outputDir: ${outputPath}`);
|
|
20296
21046
|
}
|
|
@@ -20329,7 +21079,7 @@ function walkR(dir, realMemoryDir) {
|
|
|
20329
21079
|
const results = [];
|
|
20330
21080
|
function walk(directory) {
|
|
20331
21081
|
for (const entry of fs.readdirSync(directory, { withFileTypes: true })) {
|
|
20332
|
-
const fullPath =
|
|
21082
|
+
const fullPath = path24.join(directory, entry.name);
|
|
20333
21083
|
if (entry.isSymbolicLink()) {
|
|
20334
21084
|
throw new Error(`context tree input path contains symlink: ${fullPath}`);
|
|
20335
21085
|
}
|
|
@@ -20382,13 +21132,13 @@ function extractBody(content) {
|
|
|
20382
21132
|
}
|
|
20383
21133
|
function projectNode(filePath, category, fm, rawContent) {
|
|
20384
21134
|
const body = extractBody(rawContent);
|
|
20385
|
-
const fileName =
|
|
20386
|
-
const dateDir =
|
|
21135
|
+
const fileName = path24.basename(filePath, ".md");
|
|
21136
|
+
const dateDir = path24.basename(path24.dirname(filePath));
|
|
20387
21137
|
let relPath;
|
|
20388
21138
|
if (/^\d{4}-\d{2}-\d{2}$/.test(dateDir)) {
|
|
20389
|
-
relPath =
|
|
21139
|
+
relPath = path24.join(category, dateDir, `${fileName}.md`);
|
|
20390
21140
|
} else {
|
|
20391
|
-
relPath =
|
|
21141
|
+
relPath = path24.join(category, `${fileName}.md`);
|
|
20392
21142
|
}
|
|
20393
21143
|
const generatedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
20394
21144
|
const md = `# ${fm.id}
|
|
@@ -20434,7 +21184,7 @@ function projectEntityNode(fileName, content) {
|
|
|
20434
21184
|
${content}
|
|
20435
21185
|
`;
|
|
20436
21186
|
return {
|
|
20437
|
-
path:
|
|
21187
|
+
path: path24.join("entities", `${fileName}.md`),
|
|
20438
21188
|
category: "entity",
|
|
20439
21189
|
title: fileName,
|
|
20440
21190
|
content: md,
|
|
@@ -20487,7 +21237,7 @@ function generateIndex(categoryCounts, outputDir) {
|
|
|
20487
21237
|
|
|
20488
21238
|
// src/onboarding/index.ts
|
|
20489
21239
|
import fs2 from "fs";
|
|
20490
|
-
import
|
|
21240
|
+
import path25 from "path";
|
|
20491
21241
|
var LANGUAGE_RULES = [
|
|
20492
21242
|
{
|
|
20493
21243
|
language: "TypeScript",
|
|
@@ -20589,7 +21339,7 @@ function onboard(options) {
|
|
|
20589
21339
|
maxDepth = 6,
|
|
20590
21340
|
excludeDirs = []
|
|
20591
21341
|
} = options;
|
|
20592
|
-
const directory =
|
|
21342
|
+
const directory = path25.resolve(options.directory ?? process.cwd());
|
|
20593
21343
|
let rootStat;
|
|
20594
21344
|
try {
|
|
20595
21345
|
rootStat = fs2.statSync(directory);
|
|
@@ -20631,7 +21381,7 @@ function walkDir(root, exclude, maxDepth) {
|
|
|
20631
21381
|
}
|
|
20632
21382
|
for (const entry of entries) {
|
|
20633
21383
|
if (exclude.has(entry.name)) continue;
|
|
20634
|
-
const fullPath =
|
|
21384
|
+
const fullPath = path25.join(dir, entry.name);
|
|
20635
21385
|
if (entry.isDirectory()) {
|
|
20636
21386
|
walk(fullPath, depth + 1);
|
|
20637
21387
|
} else if (entry.isFile()) {
|
|
@@ -20646,11 +21396,11 @@ function detectLanguages(files, root) {
|
|
|
20646
21396
|
const results = [];
|
|
20647
21397
|
const extCounts = /* @__PURE__ */ new Map();
|
|
20648
21398
|
for (const f of files) {
|
|
20649
|
-
const ext =
|
|
21399
|
+
const ext = path25.extname(f).toLowerCase();
|
|
20650
21400
|
if (ext) extCounts.set(ext, (extCounts.get(ext) ?? 0) + 1);
|
|
20651
21401
|
}
|
|
20652
21402
|
const rootFiles = new Set(
|
|
20653
|
-
files.filter((f) =>
|
|
21403
|
+
files.filter((f) => path25.dirname(f) === root).map((f) => path25.basename(f))
|
|
20654
21404
|
);
|
|
20655
21405
|
for (const rule of LANGUAGE_RULES) {
|
|
20656
21406
|
const evidence = [];
|
|
@@ -20694,7 +21444,7 @@ function detectLanguages(files, root) {
|
|
|
20694
21444
|
}
|
|
20695
21445
|
function detectShape(files, root) {
|
|
20696
21446
|
const rootFiles = new Set(
|
|
20697
|
-
files.filter((f) =>
|
|
21447
|
+
files.filter((f) => path25.dirname(f) === root).map((f) => path25.basename(f))
|
|
20698
21448
|
);
|
|
20699
21449
|
const rootDirs = /* @__PURE__ */ new Set();
|
|
20700
21450
|
try {
|
|
@@ -20705,7 +21455,7 @@ function detectShape(files, root) {
|
|
|
20705
21455
|
}
|
|
20706
21456
|
const evidence = [];
|
|
20707
21457
|
if (rootFiles.has("package.json")) {
|
|
20708
|
-
const pkg = readJsonSafe(
|
|
21458
|
+
const pkg = readJsonSafe(path25.join(root, "package.json"));
|
|
20709
21459
|
if (pkg?.workspaces) {
|
|
20710
21460
|
evidence.push("package.json has workspaces");
|
|
20711
21461
|
return { shape: "monorepo", evidence };
|
|
@@ -20719,13 +21469,13 @@ function detectShape(files, root) {
|
|
|
20719
21469
|
evidence.push("workspace manifest found");
|
|
20720
21470
|
return { shape: "workspace", evidence };
|
|
20721
21471
|
}
|
|
20722
|
-
const cargoToml = readTomlWorkspace(
|
|
21472
|
+
const cargoToml = readTomlWorkspace(path25.join(root, "Cargo.toml"));
|
|
20723
21473
|
if (cargoToml) {
|
|
20724
21474
|
evidence.push("Cargo.toml has workspace");
|
|
20725
21475
|
return { shape: "workspace", evidence };
|
|
20726
21476
|
}
|
|
20727
21477
|
if (rootFiles.has("package.json")) {
|
|
20728
|
-
const pkg = readJsonSafe(
|
|
21478
|
+
const pkg = readJsonSafe(path25.join(root, "package.json"));
|
|
20729
21479
|
if (pkg?.exports || pkg?.main) {
|
|
20730
21480
|
if (pkg?.bin) {
|
|
20731
21481
|
evidence.push("package.json has bin");
|
|
@@ -20759,8 +21509,8 @@ function discoverDocs(files, root) {
|
|
|
20759
21509
|
{ pattern: /^\.editorconfig$/i, kind: "config" }
|
|
20760
21510
|
];
|
|
20761
21511
|
for (const filePath of files) {
|
|
20762
|
-
const basename =
|
|
20763
|
-
const relPath =
|
|
21512
|
+
const basename = path25.basename(filePath).toLowerCase();
|
|
21513
|
+
const relPath = path25.relative(root, filePath);
|
|
20764
21514
|
let kind;
|
|
20765
21515
|
for (const { pattern, kind: k } of docPatterns) {
|
|
20766
21516
|
if (pattern.test(basename)) {
|
|
@@ -20772,7 +21522,7 @@ function discoverDocs(files, root) {
|
|
|
20772
21522
|
kind = "docs";
|
|
20773
21523
|
}
|
|
20774
21524
|
if (!kind && (basename.endsWith(".md") || basename.endsWith(".mdx"))) {
|
|
20775
|
-
if (
|
|
21525
|
+
if (path25.dirname(relPath) === "." || isUnderDocsDir(relPath)) {
|
|
20776
21526
|
kind = "docs";
|
|
20777
21527
|
}
|
|
20778
21528
|
}
|
|
@@ -20793,7 +21543,7 @@ function discoverDocs(files, root) {
|
|
|
20793
21543
|
return docs;
|
|
20794
21544
|
}
|
|
20795
21545
|
function isUnderDocsDir(relPath) {
|
|
20796
|
-
const parts = relPath.split(
|
|
21546
|
+
const parts = relPath.split(path25.sep);
|
|
20797
21547
|
return parts[0] === "docs" || parts[0] === "doc" || parts[0] === "documentation";
|
|
20798
21548
|
}
|
|
20799
21549
|
function buildPlan(languages, shape, docs, _root) {
|
|
@@ -20837,7 +21587,7 @@ function readTomlWorkspace(filePath) {
|
|
|
20837
21587
|
|
|
20838
21588
|
// src/curation/index.ts
|
|
20839
21589
|
import fs3 from "fs";
|
|
20840
|
-
import
|
|
21590
|
+
import path26 from "path";
|
|
20841
21591
|
import crypto4 from "crypto";
|
|
20842
21592
|
async function curate(options) {
|
|
20843
21593
|
const startTime = Date.now();
|
|
@@ -20928,12 +21678,12 @@ function resolveTargets(targetPath) {
|
|
|
20928
21678
|
const extensions = /* @__PURE__ */ new Set([".md", ".txt", ".mdx", ".rst"]);
|
|
20929
21679
|
function walk(dir) {
|
|
20930
21680
|
for (const entry of fs3.readdirSync(dir, { withFileTypes: true })) {
|
|
20931
|
-
const fullPath =
|
|
21681
|
+
const fullPath = path26.join(dir, entry.name);
|
|
20932
21682
|
if (entry.isDirectory()) {
|
|
20933
21683
|
if (entry.name !== "node_modules" && entry.name !== ".git") {
|
|
20934
21684
|
walk(fullPath);
|
|
20935
21685
|
}
|
|
20936
|
-
} else if (extensions.has(
|
|
21686
|
+
} else if (extensions.has(path26.extname(entry.name).toLowerCase())) {
|
|
20937
21687
|
results.push(fullPath);
|
|
20938
21688
|
}
|
|
20939
21689
|
}
|
|
@@ -20942,12 +21692,12 @@ function resolveTargets(targetPath) {
|
|
|
20942
21692
|
return results;
|
|
20943
21693
|
}
|
|
20944
21694
|
function resolveProvenanceRoot(targetPath) {
|
|
20945
|
-
const resolvedTarget =
|
|
21695
|
+
const resolvedTarget = path26.resolve(targetPath);
|
|
20946
21696
|
const stat5 = fs3.statSync(resolvedTarget);
|
|
20947
|
-
return stat5.isFile() ?
|
|
21697
|
+
return stat5.isFile() ? path26.dirname(resolvedTarget) : resolvedTarget;
|
|
20948
21698
|
}
|
|
20949
21699
|
function extractStatements(content, filePath, projectRoot, source, sourceFileHash, categoryOverride, confidence, entityRef, tags) {
|
|
20950
|
-
const relativePath =
|
|
21700
|
+
const relativePath = path26.relative(projectRoot, path26.resolve(filePath)) || path26.basename(filePath);
|
|
20951
21701
|
const statements = [];
|
|
20952
21702
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
20953
21703
|
const paragraphs = content.split(/\n{2,}/).map((p) => p.trim()).filter((p) => p.length > 20 && p.length < 2e3);
|
|
@@ -21041,7 +21791,7 @@ function loadExistingMemories(memoryDir) {
|
|
|
21041
21791
|
if (!fs3.existsSync(memoryDir)) return result;
|
|
21042
21792
|
const dirs = ALL_CATEGORY_DIRS;
|
|
21043
21793
|
for (const dir of dirs) {
|
|
21044
|
-
const fullDir =
|
|
21794
|
+
const fullDir = path26.join(memoryDir, dir);
|
|
21045
21795
|
if (!fs3.existsSync(fullDir)) continue;
|
|
21046
21796
|
walkFiles(fullDir, (filePath) => {
|
|
21047
21797
|
const content = readFileSafe(filePath);
|
|
@@ -21064,11 +21814,11 @@ function writeStatement(stmt, memoryDir) {
|
|
|
21064
21814
|
const now = /* @__PURE__ */ new Date();
|
|
21065
21815
|
const dateDir = now.toISOString().split("T")[0];
|
|
21066
21816
|
const categoryDir = getCategoryDir(memoryDir, stmt.category);
|
|
21067
|
-
const dir =
|
|
21817
|
+
const dir = path26.join(categoryDir, dateDir);
|
|
21068
21818
|
fs3.mkdirSync(dir, { recursive: true });
|
|
21069
21819
|
const fileName = `${stmt.category}-${Date.now()}-${stmt.id.slice(0, 8)}.md`;
|
|
21070
|
-
const filePath =
|
|
21071
|
-
const historicalIds = historicalIdCache2.get(
|
|
21820
|
+
const filePath = path26.join(dir, fileName);
|
|
21821
|
+
const historicalIds = historicalIdCache2.get(path26.join(memoryDir, "state"));
|
|
21072
21822
|
const rawBody = `${[
|
|
21073
21823
|
"---",
|
|
21074
21824
|
`id: ${stmt.id}`,
|
|
@@ -21091,7 +21841,7 @@ ${stmt.content}
|
|
|
21091
21841
|
fs3.writeFileSync(filePath, body);
|
|
21092
21842
|
try {
|
|
21093
21843
|
repairContentAfterJournalMoveSync({
|
|
21094
|
-
stateDir:
|
|
21844
|
+
stateDir: path26.join(memoryDir, "state"),
|
|
21095
21845
|
cache: historicalIdCache2,
|
|
21096
21846
|
idsAtWrite: historicalIds,
|
|
21097
21847
|
rawContent: rawBody,
|
|
@@ -21152,7 +21902,7 @@ function extractBody2(content) {
|
|
|
21152
21902
|
}
|
|
21153
21903
|
function walkFiles(dir, callback) {
|
|
21154
21904
|
for (const entry of fs3.readdirSync(dir, { withFileTypes: true })) {
|
|
21155
|
-
const fullPath =
|
|
21905
|
+
const fullPath = path26.join(dir, entry.name);
|
|
21156
21906
|
if (entry.isDirectory()) {
|
|
21157
21907
|
walkFiles(fullPath, callback);
|
|
21158
21908
|
} else if (entry.name.endsWith(".md")) {
|
|
@@ -21163,7 +21913,7 @@ function walkFiles(dir, callback) {
|
|
|
21163
21913
|
|
|
21164
21914
|
// src/dedup/index.ts
|
|
21165
21915
|
import fs4 from "fs";
|
|
21166
|
-
import
|
|
21916
|
+
import path27 from "path";
|
|
21167
21917
|
import crypto5 from "crypto";
|
|
21168
21918
|
var DEFAULT_DEDUP_THRESHOLD = 0.85;
|
|
21169
21919
|
var DEFAULT_MAX_LOAD = 1e4;
|
|
@@ -21305,7 +22055,7 @@ function loadMemories(memoryDir, categories, maxLoad = 1e4) {
|
|
|
21305
22055
|
const memoryRootReal = fs4.realpathSync(memoryDir);
|
|
21306
22056
|
for (const category of allCategories) {
|
|
21307
22057
|
if (result.length >= maxLoad) break;
|
|
21308
|
-
const dir =
|
|
22058
|
+
const dir = path27.join(memoryDir, category);
|
|
21309
22059
|
if (!fs4.existsSync(dir)) continue;
|
|
21310
22060
|
const categoryStat = fs4.lstatSync(dir);
|
|
21311
22061
|
if (categoryStat.isSymbolicLink()) {
|
|
@@ -21366,15 +22116,15 @@ function extractBody3(content) {
|
|
|
21366
22116
|
return match ? match[1].trim() : content.trim();
|
|
21367
22117
|
}
|
|
21368
22118
|
function assertPathInsideRoot2(rootReal, targetReal, sourcePath) {
|
|
21369
|
-
const rel =
|
|
21370
|
-
if (rel === "" || !rel.startsWith("..") && !
|
|
22119
|
+
const rel = path27.relative(rootReal, targetReal);
|
|
22120
|
+
if (rel === "" || !rel.startsWith("..") && !path27.isAbsolute(rel)) {
|
|
21371
22121
|
return;
|
|
21372
22122
|
}
|
|
21373
22123
|
throw new Error(`Refusing to scan memory path outside root: ${sourcePath}`);
|
|
21374
22124
|
}
|
|
21375
22125
|
function walkMdFiles(dir, memoryRootReal, categoryRootReal, callback) {
|
|
21376
22126
|
for (const entry of fs4.readdirSync(dir, { withFileTypes: true })) {
|
|
21377
|
-
const fullPath =
|
|
22127
|
+
const fullPath = path27.join(dir, entry.name);
|
|
21378
22128
|
const entryStat = fs4.lstatSync(fullPath);
|
|
21379
22129
|
if (entryStat.isSymbolicLink()) {
|
|
21380
22130
|
throw new Error(`Refusing to scan symlinked memory path: ${fullPath}`);
|
|
@@ -21392,10 +22142,10 @@ function walkMdFiles(dir, memoryRootReal, categoryRootReal, callback) {
|
|
|
21392
22142
|
|
|
21393
22143
|
// src/review/index.ts
|
|
21394
22144
|
import fs5 from "fs";
|
|
21395
|
-
import
|
|
22145
|
+
import path28 from "path";
|
|
21396
22146
|
var historicalIdCache3 = new HistoricalEntityCanonicalIdCache();
|
|
21397
22147
|
function writeReviewFileCanonicalized(memoryDir, filePath, content) {
|
|
21398
|
-
const stateDir =
|
|
22148
|
+
const stateDir = path28.join(memoryDir, "state");
|
|
21399
22149
|
const idsAtWrite = historicalIdCache3.get(stateDir);
|
|
21400
22150
|
let originalBytes = null;
|
|
21401
22151
|
try {
|
|
@@ -21437,8 +22187,8 @@ function realMemoryRoot(memoryDir) {
|
|
|
21437
22187
|
}
|
|
21438
22188
|
}
|
|
21439
22189
|
function isPathInside2(rootReal, candidateReal) {
|
|
21440
|
-
const relative =
|
|
21441
|
-
return relative === "" || !!relative && !relative.startsWith("..") && !
|
|
22190
|
+
const relative = path28.relative(rootReal, candidateReal);
|
|
22191
|
+
return relative === "" || !!relative && !relative.startsWith("..") && !path28.isAbsolute(relative);
|
|
21442
22192
|
}
|
|
21443
22193
|
function isSafeDirectory(rootReal, dir) {
|
|
21444
22194
|
try {
|
|
@@ -21481,7 +22231,7 @@ function listReviewItems(options) {
|
|
|
21481
22231
|
if (filterReason && item.reviewReason !== filterReason) return;
|
|
21482
22232
|
items.push(item);
|
|
21483
22233
|
};
|
|
21484
|
-
const suggestionsDir =
|
|
22234
|
+
const suggestionsDir = path28.join(memoryDir, "suggestions");
|
|
21485
22235
|
if (!isLimitReached() && fs5.existsSync(suggestionsDir) && isSafeDirectory(rootReal, suggestionsDir)) {
|
|
21486
22236
|
walkMd(rootReal, suggestionsDir, (filePath, content) => {
|
|
21487
22237
|
if (isLimitReached()) return true;
|
|
@@ -21502,7 +22252,7 @@ function listReviewItems(options) {
|
|
|
21502
22252
|
return isLimitReached();
|
|
21503
22253
|
});
|
|
21504
22254
|
}
|
|
21505
|
-
const reviewDir =
|
|
22255
|
+
const reviewDir = path28.join(memoryDir, "review");
|
|
21506
22256
|
if (!isLimitReached() && fs5.existsSync(reviewDir) && isSafeDirectory(rootReal, reviewDir)) {
|
|
21507
22257
|
walkMd(rootReal, reviewDir, (filePath, content) => {
|
|
21508
22258
|
if (isLimitReached()) return true;
|
|
@@ -21527,7 +22277,7 @@ function listReviewItems(options) {
|
|
|
21527
22277
|
const categories = ALL_CATEGORY_DIRS;
|
|
21528
22278
|
for (const category of categories) {
|
|
21529
22279
|
if (isLimitReached()) break;
|
|
21530
|
-
const dir =
|
|
22280
|
+
const dir = path28.join(memoryDir, category);
|
|
21531
22281
|
if (!fs5.existsSync(dir) || !isSafeDirectory(rootReal, dir)) continue;
|
|
21532
22282
|
walkMd(rootReal, dir, (filePath, content) => {
|
|
21533
22283
|
if (isLimitReached()) return true;
|
|
@@ -21609,9 +22359,9 @@ function approveItem(memoryDir, itemId, options) {
|
|
|
21609
22359
|
const targetDir = getCategoryDir(memoryDir, category);
|
|
21610
22360
|
const dateDir = (/* @__PURE__ */ new Date()).toISOString().split("T")[0];
|
|
21611
22361
|
ensureSafeDirectory(rootReal, targetDir);
|
|
21612
|
-
const outputPath =
|
|
21613
|
-
ensureSafeDirectory(rootReal,
|
|
21614
|
-
const reviewStateDir =
|
|
22362
|
+
const outputPath = path28.join(targetDir, dateDir, path28.basename(found.filePath));
|
|
22363
|
+
ensureSafeDirectory(rootReal, path28.dirname(outputPath));
|
|
22364
|
+
const reviewStateDir = path28.join(memoryDir, "state");
|
|
21615
22365
|
const idsAtWrite = historicalIdCache3.get(reviewStateDir);
|
|
21616
22366
|
const promotedWritten = canonicalizeEntityRefFrontmatter(updatedContent, idsAtWrite);
|
|
21617
22367
|
const promotedPath = writeFileWithoutClobber(outputPath, promotedWritten, itemId);
|
|
@@ -21688,13 +22438,13 @@ function findReviewFileById(memoryDir, id, options = {}) {
|
|
|
21688
22438
|
const rootReal = realMemoryRoot(memoryDir);
|
|
21689
22439
|
if (!rootReal) return null;
|
|
21690
22440
|
for (const loc of ["suggestions", "review"]) {
|
|
21691
|
-
const dir =
|
|
22441
|
+
const dir = path28.join(memoryDir, loc);
|
|
21692
22442
|
if (!fs5.existsSync(dir) || !isSafeDirectory(rootReal, dir)) continue;
|
|
21693
22443
|
const found = findFileById(rootReal, dir, id);
|
|
21694
22444
|
if (found) return { filePath: found, location: "queue" };
|
|
21695
22445
|
}
|
|
21696
22446
|
for (const category of ALL_CATEGORY_DIRS) {
|
|
21697
|
-
const dir =
|
|
22447
|
+
const dir = path28.join(memoryDir, category);
|
|
21698
22448
|
if (!fs5.existsSync(dir) || !isSafeDirectory(rootReal, dir)) continue;
|
|
21699
22449
|
const found = findFileById(rootReal, dir, id, (fm) => isLowConfidenceReviewCandidate(fm, options));
|
|
21700
22450
|
if (found) return { filePath: found, location: "category" };
|
|
@@ -21770,10 +22520,10 @@ function readFileSafe3(filePath) {
|
|
|
21770
22520
|
}
|
|
21771
22521
|
}
|
|
21772
22522
|
function writeFileWithoutClobber(basePath, content, discriminator) {
|
|
21773
|
-
const parsed =
|
|
22523
|
+
const parsed = path28.parse(basePath);
|
|
21774
22524
|
const safeDiscriminator = sanitizeFilePart(discriminator);
|
|
21775
22525
|
for (let attempt = 0; attempt < 1e3; attempt++) {
|
|
21776
|
-
const candidate = attempt === 0 ? basePath :
|
|
22526
|
+
const candidate = attempt === 0 ? basePath : path28.join(
|
|
21777
22527
|
parsed.dir,
|
|
21778
22528
|
`${parsed.name}-${safeDiscriminator}${attempt === 1 ? "" : `-${attempt}`}${parsed.ext || ".md"}`
|
|
21779
22529
|
);
|
|
@@ -21829,7 +22579,7 @@ function extractBody4(content) {
|
|
|
21829
22579
|
function walkMd(rootReal, dir, callback) {
|
|
21830
22580
|
if (!isSafeDirectory(rootReal, dir)) return false;
|
|
21831
22581
|
for (const entry of fs5.readdirSync(dir, { withFileTypes: true })) {
|
|
21832
|
-
const fullPath =
|
|
22582
|
+
const fullPath = path28.join(dir, entry.name);
|
|
21833
22583
|
if (entry.isSymbolicLink()) continue;
|
|
21834
22584
|
if (entry.isDirectory()) {
|
|
21835
22585
|
if (walkMd(rootReal, fullPath, callback)) return true;
|
|
@@ -21844,7 +22594,7 @@ function walkMdPaths(rootReal, dir) {
|
|
|
21844
22594
|
const results = [];
|
|
21845
22595
|
if (!isSafeDirectory(rootReal, dir)) return results;
|
|
21846
22596
|
for (const entry of fs5.readdirSync(dir, { withFileTypes: true })) {
|
|
21847
|
-
const fullPath =
|
|
22597
|
+
const fullPath = path28.join(dir, entry.name);
|
|
21848
22598
|
if (entry.isSymbolicLink()) continue;
|
|
21849
22599
|
if (entry.isDirectory()) {
|
|
21850
22600
|
results.push(...walkMdPaths(rootReal, fullPath));
|
|
@@ -21857,7 +22607,7 @@ function walkMdPaths(rootReal, dir) {
|
|
|
21857
22607
|
|
|
21858
22608
|
// src/sync/index.ts
|
|
21859
22609
|
import fs6 from "fs";
|
|
21860
|
-
import
|
|
22610
|
+
import path29 from "path";
|
|
21861
22611
|
import crypto6 from "crypto";
|
|
21862
22612
|
var DEFAULT_EXTENSIONS = /* @__PURE__ */ new Set([".md", ".txt", ".mdx", ".rst"]);
|
|
21863
22613
|
var DEFAULT_EXCLUDE2 = /* @__PURE__ */ new Set([
|
|
@@ -21879,7 +22629,7 @@ function syncChanges(options) {
|
|
|
21879
22629
|
} = options;
|
|
21880
22630
|
const extSet = new Set(extensions);
|
|
21881
22631
|
const excludeSet = /* @__PURE__ */ new Set([...DEFAULT_EXCLUDE2, ...excludeDirs]);
|
|
21882
|
-
const stateFilePath = options.stateFile ??
|
|
22632
|
+
const stateFilePath = options.stateFile ?? path29.join(memoryDir, ".sync-state.json");
|
|
21883
22633
|
const prevState = loadState(stateFilePath);
|
|
21884
22634
|
const currentFiles = scanFiles(sourceDir, extSet, excludeSet);
|
|
21885
22635
|
const changes = computeDiff(currentFiles, prevState.fileHashes, sourceDir);
|
|
@@ -21895,7 +22645,7 @@ function syncChanges(options) {
|
|
|
21895
22645
|
for (const [relPath, hash] of Object.entries(currentFiles)) {
|
|
21896
22646
|
newState.fileHashes[relPath] = hash;
|
|
21897
22647
|
}
|
|
21898
|
-
fs6.mkdirSync(
|
|
22648
|
+
fs6.mkdirSync(path29.dirname(stateFilePath), { recursive: true });
|
|
21899
22649
|
fs6.writeFileSync(stateFilePath, JSON.stringify(newState, null, 2));
|
|
21900
22650
|
}
|
|
21901
22651
|
return {
|
|
@@ -21961,13 +22711,13 @@ function scanFiles(root, extensions, exclude) {
|
|
|
21961
22711
|
}
|
|
21962
22712
|
for (const entry of entries) {
|
|
21963
22713
|
if (exclude.has(entry.name)) continue;
|
|
21964
|
-
const fullPath =
|
|
22714
|
+
const fullPath = path29.join(dir, entry.name);
|
|
21965
22715
|
if (entry.isDirectory()) {
|
|
21966
22716
|
walk(fullPath);
|
|
21967
22717
|
} else if (entry.isFile()) {
|
|
21968
|
-
const ext =
|
|
22718
|
+
const ext = path29.extname(entry.name).toLowerCase();
|
|
21969
22719
|
if (!extensions.has(ext)) continue;
|
|
21970
|
-
const relPath =
|
|
22720
|
+
const relPath = path29.relative(root, fullPath);
|
|
21971
22721
|
try {
|
|
21972
22722
|
const content = fs6.readFileSync(fullPath, "utf8");
|
|
21973
22723
|
result[relPath] = hashContent3(content);
|
|
@@ -21982,7 +22732,7 @@ function scanFiles(root, extensions, exclude) {
|
|
|
21982
22732
|
function computeDiff(current, previous, sourceDir) {
|
|
21983
22733
|
const changes = [];
|
|
21984
22734
|
for (const [relPath, hash] of Object.entries(current)) {
|
|
21985
|
-
const fullPath =
|
|
22735
|
+
const fullPath = path29.join(sourceDir, relPath);
|
|
21986
22736
|
if (!(relPath in previous)) {
|
|
21987
22737
|
let size = 0;
|
|
21988
22738
|
try {
|
|
@@ -22015,7 +22765,7 @@ function computeDiff(current, previous, sourceDir) {
|
|
|
22015
22765
|
for (const relPath of Object.keys(previous)) {
|
|
22016
22766
|
if (!(relPath in current)) {
|
|
22017
22767
|
changes.push({
|
|
22018
|
-
filePath:
|
|
22768
|
+
filePath: path29.join(sourceDir, relPath),
|
|
22019
22769
|
relativePath: relPath,
|
|
22020
22770
|
type: "deleted",
|
|
22021
22771
|
currentHash: "",
|
|
@@ -22045,21 +22795,21 @@ function hashContent3(content) {
|
|
|
22045
22795
|
import { spawnSync } from "child_process";
|
|
22046
22796
|
import crypto7 from "crypto";
|
|
22047
22797
|
import fs7 from "fs";
|
|
22048
|
-
import
|
|
22798
|
+
import path30 from "path";
|
|
22049
22799
|
var historicalIdCache4 = new HistoricalEntityCanonicalIdCache();
|
|
22050
22800
|
var MANIFEST_VERSION = 1;
|
|
22051
22801
|
var MANIFEST_LOCK_STALE_MS = 3e4;
|
|
22052
22802
|
var MANIFEST_LOCK_TIMEOUT_MS = MANIFEST_LOCK_STALE_MS + 1e4;
|
|
22053
22803
|
var MANIFEST_LOCK_SLEEP_MS = 20;
|
|
22054
22804
|
function normalizeSpaceMemoryDir(memoryDir) {
|
|
22055
|
-
return
|
|
22805
|
+
return path30.resolve(memoryDir);
|
|
22056
22806
|
}
|
|
22057
22807
|
function getSpacesDir(baseDir) {
|
|
22058
22808
|
const homeDir = baseDir ?? resolveHomeDir();
|
|
22059
|
-
return
|
|
22809
|
+
return path30.join(homeDir, ".config", "engram", "spaces");
|
|
22060
22810
|
}
|
|
22061
22811
|
function getManifestPath(baseDir) {
|
|
22062
|
-
return
|
|
22812
|
+
return path30.join(getSpacesDir(baseDir), "manifest.json");
|
|
22063
22813
|
}
|
|
22064
22814
|
function loadManifest(baseDir, memoryDirOverride) {
|
|
22065
22815
|
if (fs7.existsSync(getManifestPath(baseDir))) {
|
|
@@ -22106,9 +22856,9 @@ function readManifestUnlocked(baseDir, memoryDirOverride, options = {}) {
|
|
|
22106
22856
|
}
|
|
22107
22857
|
function saveManifestUnlocked(manifest, baseDir) {
|
|
22108
22858
|
const manifestPath2 = getManifestPath(baseDir);
|
|
22109
|
-
const manifestDir2 =
|
|
22859
|
+
const manifestDir2 = path30.dirname(manifestPath2);
|
|
22110
22860
|
fs7.mkdirSync(manifestDir2, { recursive: true });
|
|
22111
|
-
const tempPath =
|
|
22861
|
+
const tempPath = path30.join(manifestDir2, `.manifest.${process.pid}.${Date.now()}.${crypto7.randomUUID()}.tmp`);
|
|
22112
22862
|
try {
|
|
22113
22863
|
fs7.writeFileSync(tempPath, `${JSON.stringify(manifest, null, 2)}
|
|
22114
22864
|
`, { flag: "wx" });
|
|
@@ -22123,7 +22873,7 @@ function saveManifestUnlocked(manifest, baseDir) {
|
|
|
22123
22873
|
}
|
|
22124
22874
|
function withManifestLock(baseDir, operation) {
|
|
22125
22875
|
const lockDir = `${getManifestPath(baseDir)}.lock`;
|
|
22126
|
-
fs7.mkdirSync(
|
|
22876
|
+
fs7.mkdirSync(path30.dirname(lockDir), { recursive: true });
|
|
22127
22877
|
const lockOwner = acquireManifestLock(lockDir);
|
|
22128
22878
|
try {
|
|
22129
22879
|
return operation();
|
|
@@ -22149,7 +22899,7 @@ function acquireManifestLock(lockDir) {
|
|
|
22149
22899
|
try {
|
|
22150
22900
|
fs7.mkdirSync(lockDir, { recursive: false });
|
|
22151
22901
|
try {
|
|
22152
|
-
fs7.writeFileSync(
|
|
22902
|
+
fs7.writeFileSync(path30.join(lockDir, "owner"), `${owner}
|
|
22153
22903
|
`, { flag: "wx" });
|
|
22154
22904
|
} catch (error) {
|
|
22155
22905
|
fs7.rmSync(lockDir, { recursive: true, force: true });
|
|
@@ -22179,7 +22929,7 @@ function acquireManifestLock(lockDir) {
|
|
|
22179
22929
|
}
|
|
22180
22930
|
function releaseManifestLock(lockDir, owner) {
|
|
22181
22931
|
try {
|
|
22182
|
-
const ownerPath =
|
|
22932
|
+
const ownerPath = path30.join(lockDir, "owner");
|
|
22183
22933
|
if (fs7.readFileSync(ownerPath, "utf8").trim() === owner) {
|
|
22184
22934
|
fs7.rmSync(lockDir, { recursive: true, force: true });
|
|
22185
22935
|
}
|
|
@@ -22195,7 +22945,7 @@ function removeStaleManifestLock(lockDir) {
|
|
|
22195
22945
|
try {
|
|
22196
22946
|
fs7.mkdirSync(reclaimDir, { recursive: false });
|
|
22197
22947
|
try {
|
|
22198
|
-
fs7.writeFileSync(
|
|
22948
|
+
fs7.writeFileSync(path30.join(reclaimDir, "owner"), `${reclaimOwner}
|
|
22199
22949
|
`, { flag: "wx" });
|
|
22200
22950
|
} catch (error) {
|
|
22201
22951
|
fs7.rmSync(reclaimDir, { recursive: true, force: true });
|
|
@@ -22270,7 +23020,7 @@ function readManifestLockSnapshot(lockDir) {
|
|
|
22270
23020
|
throw error;
|
|
22271
23021
|
}
|
|
22272
23022
|
try {
|
|
22273
|
-
const owner = fs7.readFileSync(
|
|
23023
|
+
const owner = fs7.readFileSync(path30.join(lockDir, "owner"), "utf8").trim();
|
|
22274
23024
|
return { mtimeMs: stat5.mtimeMs, owner };
|
|
22275
23025
|
} catch (error) {
|
|
22276
23026
|
if (error.code === "ENOENT") {
|
|
@@ -22342,8 +23092,8 @@ function sleepSync(ms) {
|
|
|
22342
23092
|
}
|
|
22343
23093
|
function createPersonalSpace(baseDir, memoryDirOverride) {
|
|
22344
23094
|
const homeDir = baseDir ?? resolveHomeDir();
|
|
22345
|
-
const standalonePath =
|
|
22346
|
-
const openclawPath =
|
|
23095
|
+
const standalonePath = path30.join(homeDir, ".engram", "memory");
|
|
23096
|
+
const openclawPath = path30.join(homeDir, ".openclaw", "workspace", "memory", "local");
|
|
22347
23097
|
const memoryDir = memoryDirOverride ?? readEnvVar("REMNIC_MEMORY_DIR") ?? readEnvVar("ENGRAM_MEMORY_DIR") ?? (fs7.existsSync(standalonePath) ? standalonePath : fs7.existsSync(openclawPath) ? openclawPath : standalonePath);
|
|
22348
23098
|
const normalizedMemoryDir = normalizeSpaceMemoryDir(memoryDir);
|
|
22349
23099
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
@@ -22372,7 +23122,7 @@ function createSpace(options) {
|
|
|
22372
23122
|
const id = options.name.toLowerCase().replace(/[^a-z0-9-]/g, "-").replace(/-+/g, "-");
|
|
22373
23123
|
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
22374
23124
|
const memoryDir = normalizeSpaceMemoryDir(
|
|
22375
|
-
options.memoryDir ??
|
|
23125
|
+
options.memoryDir ?? path30.join(getSpacesDir(options.baseDir), id, "memory")
|
|
22376
23126
|
);
|
|
22377
23127
|
const space = updateManifest(options.baseDir, (manifest) => {
|
|
22378
23128
|
if (manifest.spaces.some((s) => s.id === id)) {
|
|
@@ -22593,14 +23343,14 @@ async function mergeSpaces(sourceSpaceId, targetSpaceId, options) {
|
|
|
22593
23343
|
};
|
|
22594
23344
|
}
|
|
22595
23345
|
function getAuditLog(baseDir) {
|
|
22596
|
-
const auditPath =
|
|
23346
|
+
const auditPath = path30.join(getSpacesDir(baseDir), "audit.jsonl");
|
|
22597
23347
|
if (!fs7.existsSync(auditPath)) return [];
|
|
22598
23348
|
const lines = fs7.readFileSync(auditPath, "utf8").trim().split("\n");
|
|
22599
23349
|
return lines.filter((l) => l.trim()).map((l) => JSON.parse(l));
|
|
22600
23350
|
}
|
|
22601
23351
|
function appendAudit(entry, baseDir) {
|
|
22602
|
-
const auditPath =
|
|
22603
|
-
fs7.mkdirSync(
|
|
23352
|
+
const auditPath = path30.join(getSpacesDir(baseDir), "audit.jsonl");
|
|
23353
|
+
fs7.mkdirSync(path30.dirname(auditPath), { recursive: true });
|
|
22604
23354
|
const full = {
|
|
22605
23355
|
id: crypto7.randomUUID(),
|
|
22606
23356
|
timestamp: (/* @__PURE__ */ new Date()).toISOString(),
|
|
@@ -22621,11 +23371,11 @@ async function copyMemories(sourceDir, targetDir, options) {
|
|
|
22621
23371
|
sourceFiles.filter((p) => {
|
|
22622
23372
|
const rp = safeRealpath(p);
|
|
22623
23373
|
if (!rp || !isPathInsideRoot(rp, sourceRoot)) return false;
|
|
22624
|
-
const rel =
|
|
22625
|
-
const mapped =
|
|
23374
|
+
const rel = path30.relative(sourceRoot, rp);
|
|
23375
|
+
const mapped = path30.resolve(targetRoot, rel);
|
|
22626
23376
|
if (!isPathInsideRoot(mapped, targetRoot)) return false;
|
|
22627
23377
|
return classifyEntityRefWritePath(targetRoot, mapped) === "entity";
|
|
22628
|
-
}).map((p) =>
|
|
23378
|
+
}).map((p) => path30.basename(p, ".md"))
|
|
22629
23379
|
);
|
|
22630
23380
|
const firstEntityId = sourceEntityIds.values().next().value;
|
|
22631
23381
|
if (firstEntityId === void 0) {
|
|
@@ -22633,7 +23383,7 @@ async function copyMemories(sourceDir, targetDir, options) {
|
|
|
22633
23383
|
}
|
|
22634
23384
|
return withRawEntityPageMutation(
|
|
22635
23385
|
targetRoot,
|
|
22636
|
-
|
|
23386
|
+
path30.join(targetRoot, "entities", `${firstEntityId}.md`),
|
|
22637
23387
|
async () => copyPreparedMemories(
|
|
22638
23388
|
sourceFiles,
|
|
22639
23389
|
sourceRoot,
|
|
@@ -22660,14 +23410,14 @@ function copyPreparedMemories(sourceFiles, sourceRoot, targetRoot, sourceEntityI
|
|
|
22660
23410
|
continue;
|
|
22661
23411
|
}
|
|
22662
23412
|
const content = fs7.readFileSync(sourcePath, "utf8");
|
|
22663
|
-
const relativePath =
|
|
22664
|
-
const targetPath =
|
|
23413
|
+
const relativePath = path30.relative(sourceRoot, sourceRealPath);
|
|
23414
|
+
const targetPath = path30.resolve(targetRoot, relativePath);
|
|
22665
23415
|
if (!isPathInsideRoot(targetPath, targetRoot)) {
|
|
22666
23416
|
skipped++;
|
|
22667
23417
|
continue;
|
|
22668
23418
|
}
|
|
22669
23419
|
const targetKind = classifyEntityRefWritePath(targetRoot, targetPath);
|
|
22670
|
-
const idsAtCompare = historicalIdCache4.get(
|
|
23420
|
+
const idsAtCompare = historicalIdCache4.get(path30.join(targetRoot, "state"));
|
|
22671
23421
|
const sourceRef = targetKind === "memory" ? readEntityRefFromFrontmatter(content) : null;
|
|
22672
23422
|
const refHasSourceClaimant = sourceRef !== null && sourceEntityIds.has(sourceRef);
|
|
22673
23423
|
const canonicalContent = targetKind === "memory" && !refHasSourceClaimant ? canonicalizeEntityRefFrontmatter(content, idsAtCompare) : content;
|
|
@@ -22694,7 +23444,7 @@ function copyPreparedMemories(sourceFiles, sourceRoot, targetRoot, sourceEntityI
|
|
|
22694
23444
|
if (fs7.existsSync(targetPath) && !options?.force) {
|
|
22695
23445
|
const targetContent = fs7.readFileSync(targetPath, "utf8");
|
|
22696
23446
|
const targetHash = hashContent4(targetContent);
|
|
22697
|
-
if (hashContent4(canonicalContent) === targetHash && historicalIdCache4.get(
|
|
23447
|
+
if (hashContent4(canonicalContent) === targetHash && historicalIdCache4.get(path30.join(targetRoot, "state")) === idsAtCompare) {
|
|
22698
23448
|
skipped++;
|
|
22699
23449
|
continue;
|
|
22700
23450
|
}
|
|
@@ -22710,13 +23460,13 @@ function copyPreparedMemories(sourceFiles, sourceRoot, targetRoot, sourceEntityI
|
|
|
22710
23460
|
continue;
|
|
22711
23461
|
}
|
|
22712
23462
|
}
|
|
22713
|
-
fs7.mkdirSync(
|
|
22714
|
-
const targetParentRealPath = safeRealpath(
|
|
23463
|
+
fs7.mkdirSync(path30.dirname(targetPath), { recursive: true });
|
|
23464
|
+
const targetParentRealPath = safeRealpath(path30.dirname(targetPath));
|
|
22715
23465
|
if (!targetParentRealPath || !isPathInsideRoot(targetParentRealPath, targetRoot)) {
|
|
22716
23466
|
skipped++;
|
|
22717
23467
|
continue;
|
|
22718
23468
|
}
|
|
22719
|
-
const stateDir =
|
|
23469
|
+
const stateDir = path30.join(targetRoot, "state");
|
|
22720
23470
|
if (targetKind === "memory" && !refHasSourceClaimant) {
|
|
22721
23471
|
const idsAtWrite = historicalIdCache4.get(stateDir);
|
|
22722
23472
|
const written = canonicalizeEntityRefFrontmatter(content, idsAtWrite);
|
|
@@ -22760,7 +23510,7 @@ function copyPreparedMemories(sourceFiles, sourceRoot, targetRoot, sourceEntityI
|
|
|
22760
23510
|
bumpMemoryCorpusVersionForDir(targetRoot);
|
|
22761
23511
|
}
|
|
22762
23512
|
if (reconcileNeeded) {
|
|
22763
|
-
requestEntityCanonicalIdReconcileSync(
|
|
23513
|
+
requestEntityCanonicalIdReconcileSync(path30.join(targetRoot, "state"));
|
|
22764
23514
|
}
|
|
22765
23515
|
return { merged, conflicts, skipped };
|
|
22766
23516
|
}
|
|
@@ -22771,7 +23521,7 @@ function walkMd2(dir) {
|
|
|
22771
23521
|
const results = [];
|
|
22772
23522
|
function walk(d) {
|
|
22773
23523
|
for (const entry of fs7.readdirSync(d, { withFileTypes: true })) {
|
|
22774
|
-
const fullPath =
|
|
23524
|
+
const fullPath = path30.join(d, entry.name);
|
|
22775
23525
|
if (entry.isSymbolicLink()) {
|
|
22776
23526
|
continue;
|
|
22777
23527
|
}
|
|
@@ -22800,8 +23550,8 @@ function safeRealpath(filePath) {
|
|
|
22800
23550
|
}
|
|
22801
23551
|
}
|
|
22802
23552
|
function isPathInsideRoot(candidatePath, rootPath) {
|
|
22803
|
-
const relative =
|
|
22804
|
-
return relative === "" || !relative.startsWith("..") && !
|
|
23553
|
+
const relative = path30.relative(rootPath, candidatePath);
|
|
23554
|
+
return relative === "" || !relative.startsWith("..") && !path30.isAbsolute(relative);
|
|
22805
23555
|
}
|
|
22806
23556
|
function parseSimpleFrontmatter(content) {
|
|
22807
23557
|
const match = content.match(/^---\n([\s\S]*?)\n---/);
|
|
@@ -22922,7 +23672,7 @@ var REMNIC_RECALL_DECISION_RULES = `## When to Use Recall vs Direct Read
|
|
|
22922
23672
|
// src/memory-extension/codex-publisher.ts
|
|
22923
23673
|
import fs8 from "fs";
|
|
22924
23674
|
import os from "os";
|
|
22925
|
-
import
|
|
23675
|
+
import path31 from "path";
|
|
22926
23676
|
var REMNIC_EXTENSION_DIR_NAME = "remnic";
|
|
22927
23677
|
function resolveEnvHome(env) {
|
|
22928
23678
|
if (env === void 0) return resolveHomeDir();
|
|
@@ -22931,12 +23681,12 @@ function resolveEnvHome(env) {
|
|
|
22931
23681
|
function expandTildeWithHome(input, homeDir) {
|
|
22932
23682
|
if (input === "~") return homeDir;
|
|
22933
23683
|
if (input.startsWith("~/") || input.startsWith("~\\")) {
|
|
22934
|
-
return
|
|
23684
|
+
return path31.join(homeDir, input.slice(2));
|
|
22935
23685
|
}
|
|
22936
23686
|
return input;
|
|
22937
23687
|
}
|
|
22938
23688
|
function normalizeHostRoot(input, homeDir) {
|
|
22939
|
-
return
|
|
23689
|
+
return path31.resolve(expandTildeWithHome(input.trim(), homeDir));
|
|
22940
23690
|
}
|
|
22941
23691
|
var CodexMemoryExtensionPublisher = class {
|
|
22942
23692
|
hostId = "codex";
|
|
@@ -22950,12 +23700,12 @@ var CodexMemoryExtensionPublisher = class {
|
|
|
22950
23700
|
async resolveExtensionRoot(env) {
|
|
22951
23701
|
const homeDir = resolveEnvHome(env);
|
|
22952
23702
|
const codexHomeInput = env === void 0 ? readEnvVar("CODEX_HOME")?.trim() : env.CODEX_HOME?.trim();
|
|
22953
|
-
const codexHome = codexHomeInput ? normalizeHostRoot(codexHomeInput, homeDir) :
|
|
22954
|
-
return
|
|
23703
|
+
const codexHome = codexHomeInput ? normalizeHostRoot(codexHomeInput, homeDir) : path31.resolve(homeDir, ".codex");
|
|
23704
|
+
return path31.join(codexHome, "memories_extensions", REMNIC_EXTENSION_DIR_NAME);
|
|
22955
23705
|
}
|
|
22956
23706
|
async isHostAvailable() {
|
|
22957
23707
|
try {
|
|
22958
|
-
const home = readEnvVar("CODEX_HOME")?.trim() ||
|
|
23708
|
+
const home = readEnvVar("CODEX_HOME")?.trim() || path31.join(resolveHomeDir(), ".codex");
|
|
22959
23709
|
return fs8.existsSync(home);
|
|
22960
23710
|
} catch {
|
|
22961
23711
|
return false;
|
|
@@ -23006,7 +23756,7 @@ When running inside the Codex phase-2 consolidation sandbox:
|
|
|
23006
23756
|
}
|
|
23007
23757
|
async publish(ctx) {
|
|
23008
23758
|
const extensionRoot = await this.resolveExtensionRoot();
|
|
23009
|
-
const instructionsPath =
|
|
23759
|
+
const instructionsPath = path31.join(extensionRoot, "instructions.md");
|
|
23010
23760
|
const filesWritten = [];
|
|
23011
23761
|
const skipped = [];
|
|
23012
23762
|
ctx.log.info(`Publishing Codex memory extension to ${extensionRoot}`);
|
|
@@ -23381,8 +24131,8 @@ async function generateActivityMemories(date, digestBody, config, deps) {
|
|
|
23381
24131
|
|
|
23382
24132
|
// src/session-summaries/index.ts
|
|
23383
24133
|
import { createHash as createHash7 } from "crypto";
|
|
23384
|
-
import { lstat as
|
|
23385
|
-
import
|
|
24134
|
+
import { lstat as lstat3, mkdir as mkdir7, readFile as readFile6, readdir as readdir4, rename, rm, stat as stat4, writeFile as writeFile7 } from "fs/promises";
|
|
24135
|
+
import path32 from "path";
|
|
23386
24136
|
|
|
23387
24137
|
// src/session-summaries/adapters.ts
|
|
23388
24138
|
var VALID_ROLES = /* @__PURE__ */ new Set(["user", "assistant", "tool", "system", "other"]);
|
|
@@ -23887,7 +24637,7 @@ function shortHash(value, length = 16) {
|
|
|
23887
24637
|
async function listTranscriptFiles(root, maxFiles) {
|
|
23888
24638
|
const out = [];
|
|
23889
24639
|
let truncated = false;
|
|
23890
|
-
const entrySortKey = (entryName, isDirectory) => isDirectory ? `${entryName}${
|
|
24640
|
+
const entrySortKey = (entryName, isDirectory) => isDirectory ? `${entryName}${path32.sep}` : entryName;
|
|
23891
24641
|
async function visit(dir) {
|
|
23892
24642
|
if (truncated) return;
|
|
23893
24643
|
const entries = (await readdir4(dir, { withFileTypes: true })).sort(
|
|
@@ -23897,13 +24647,13 @@ async function listTranscriptFiles(root, maxFiles) {
|
|
|
23897
24647
|
if (truncated) return;
|
|
23898
24648
|
if (entry.name.startsWith(".")) continue;
|
|
23899
24649
|
if (entry.isSymbolicLink()) continue;
|
|
23900
|
-
const fullPath =
|
|
24650
|
+
const fullPath = path32.join(dir, entry.name);
|
|
23901
24651
|
if (entry.isDirectory()) {
|
|
23902
24652
|
await visit(fullPath);
|
|
23903
24653
|
continue;
|
|
23904
24654
|
}
|
|
23905
24655
|
if (!entry.isFile()) continue;
|
|
23906
|
-
const ext =
|
|
24656
|
+
const ext = path32.extname(entry.name).toLowerCase();
|
|
23907
24657
|
if (!SUPPORTED_EXTENSIONS.has(ext)) continue;
|
|
23908
24658
|
out.push(fullPath);
|
|
23909
24659
|
if (out.length > maxFiles) {
|
|
@@ -23930,7 +24680,7 @@ function normalizeInputDir(inputDir) {
|
|
|
23930
24680
|
if (typeof inputDir !== "string" || inputDir.trim().length === 0) {
|
|
23931
24681
|
throw new Error("inputDir must be a non-empty string");
|
|
23932
24682
|
}
|
|
23933
|
-
return
|
|
24683
|
+
return path32.resolve(expandTildePath(inputDir.trim()));
|
|
23934
24684
|
}
|
|
23935
24685
|
function initRoleCounts() {
|
|
23936
24686
|
return {
|
|
@@ -24025,7 +24775,7 @@ function buildDraft(options) {
|
|
|
24025
24775
|
}
|
|
24026
24776
|
async function collectLocalSessionSummaries(options) {
|
|
24027
24777
|
const inputDir = normalizeInputDir(options.inputDir);
|
|
24028
|
-
const inputLstat = await
|
|
24778
|
+
const inputLstat = await lstat3(inputDir);
|
|
24029
24779
|
if (inputLstat.isSymbolicLink()) {
|
|
24030
24780
|
throw new Error(`inputDir must not be a symbolic link: ${options.inputDir}`);
|
|
24031
24781
|
}
|
|
@@ -24087,11 +24837,11 @@ async function collectLocalSessionSummaries(options) {
|
|
|
24087
24837
|
continue;
|
|
24088
24838
|
}
|
|
24089
24839
|
seenFileHashes.add(fileHash);
|
|
24090
|
-
const fileExtension =
|
|
24840
|
+
const fileExtension = path32.extname(filePath).toLowerCase();
|
|
24091
24841
|
const parsed = await adapter.parseFile(
|
|
24092
24842
|
{
|
|
24093
24843
|
content,
|
|
24094
|
-
fileName:
|
|
24844
|
+
fileName: path32.basename(filePath),
|
|
24095
24845
|
fileExtension,
|
|
24096
24846
|
fileRef: fileHash
|
|
24097
24847
|
},
|
|
@@ -24147,7 +24897,7 @@ async function collectLocalSessionSummaries(options) {
|
|
|
24147
24897
|
}
|
|
24148
24898
|
async function readRedactionConfig(pathLike) {
|
|
24149
24899
|
if (!pathLike) return void 0;
|
|
24150
|
-
const raw = await readFile6(
|
|
24900
|
+
const raw = await readFile6(path32.resolve(expandTildePath(pathLike)), "utf-8");
|
|
24151
24901
|
const parsed = JSON.parse(raw);
|
|
24152
24902
|
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
24153
24903
|
throw new Error("redaction config must be a JSON object");
|
|
@@ -24160,15 +24910,15 @@ function toJsonl(drafts) {
|
|
|
24160
24910
|
}
|
|
24161
24911
|
function defaultDraftOutputPath(memoryDir, generatedAt) {
|
|
24162
24912
|
const stamp = generatedAt.replace(/[:.]/g, "-");
|
|
24163
|
-
return
|
|
24164
|
-
|
|
24913
|
+
return path32.join(
|
|
24914
|
+
path32.resolve(expandTildePath(memoryDir)),
|
|
24165
24915
|
"state",
|
|
24166
24916
|
"session-summary-drafts",
|
|
24167
24917
|
`session-summaries-${stamp}.jsonl`
|
|
24168
24918
|
);
|
|
24169
24919
|
}
|
|
24170
24920
|
async function writeDrafts(filePath, drafts) {
|
|
24171
|
-
await mkdir7(
|
|
24921
|
+
await mkdir7(path32.dirname(filePath), { recursive: true });
|
|
24172
24922
|
const tempPath = `${filePath}.${process.pid}.${Date.now()}.tmp`;
|
|
24173
24923
|
try {
|
|
24174
24924
|
await writeFile7(tempPath, toJsonl(drafts), "utf-8");
|
|
@@ -24186,7 +24936,7 @@ async function runLocalSessionSummaryCliCommand(options) {
|
|
|
24186
24936
|
});
|
|
24187
24937
|
const wroteFiles = [];
|
|
24188
24938
|
if (options.output) {
|
|
24189
|
-
const outputPath =
|
|
24939
|
+
const outputPath = path32.resolve(expandTildePath(options.output));
|
|
24190
24940
|
await writeDrafts(outputPath, report.drafts);
|
|
24191
24941
|
wroteFiles.push(outputPath);
|
|
24192
24942
|
}
|
|
@@ -24220,20 +24970,20 @@ async function runLocalSessionSummaryCliCommand(options) {
|
|
|
24220
24970
|
}
|
|
24221
24971
|
|
|
24222
24972
|
// src/transfer/capsule-fork.ts
|
|
24223
|
-
import { lstat as
|
|
24224
|
-
import
|
|
24973
|
+
import { lstat as lstat4, mkdir as mkdir8, readFile as readFile7, realpath as realpath3, writeFile as writeFile8 } from "fs/promises";
|
|
24974
|
+
import path33 from "path";
|
|
24225
24975
|
async function forkCapsule(opts) {
|
|
24226
24976
|
validateForkId(opts.forkId);
|
|
24227
|
-
const rootAbs =
|
|
24977
|
+
const rootAbs = path33.resolve(opts.targetRoot);
|
|
24228
24978
|
await assertIsDirectoryNotSymlink(rootAbs, "forkCapsule", "targetRoot");
|
|
24229
|
-
const forkDirAbs =
|
|
24979
|
+
const forkDirAbs = path33.join(rootAbs, "forks", opts.forkId);
|
|
24230
24980
|
const forkEntryExists = await pathEntryExists(forkDirAbs);
|
|
24231
24981
|
if (forkEntryExists) {
|
|
24232
24982
|
throw new Error(
|
|
24233
24983
|
`forkCapsule: fork path already exists \u2014 forkId "${opts.forkId}" is already in use at: ${forkDirAbs}`
|
|
24234
24984
|
);
|
|
24235
24985
|
}
|
|
24236
|
-
const archiveAbs =
|
|
24986
|
+
const archiveAbs = path33.resolve(opts.sourceArchive);
|
|
24237
24987
|
const importResult = await importCapsule({
|
|
24238
24988
|
archivePath: archiveAbs,
|
|
24239
24989
|
root: rootAbs,
|
|
@@ -24255,10 +25005,10 @@ async function forkCapsule(opts) {
|
|
|
24255
25005
|
importedRecords: importResult.imported.length,
|
|
24256
25006
|
skippedRecords: importResult.skipped.length
|
|
24257
25007
|
};
|
|
24258
|
-
const lineagePath =
|
|
24259
|
-
const rootReal = await
|
|
25008
|
+
const lineagePath = path33.join(forkDirAbs, "lineage.json");
|
|
25009
|
+
const rootReal = await realpath3(rootAbs);
|
|
24260
25010
|
await assertRealpathInsideRoot(rootReal, lineagePath, `forks/${opts.forkId}/lineage.json`, "forkCapsule");
|
|
24261
|
-
await mkdir8(
|
|
25011
|
+
await mkdir8(path33.dirname(lineagePath), { recursive: true });
|
|
24262
25012
|
await writeFile8(lineagePath, JSON.stringify(lineage, null, 2) + "\n", "utf-8");
|
|
24263
25013
|
return {
|
|
24264
25014
|
archivePath: archiveAbs,
|
|
@@ -24272,11 +25022,11 @@ async function readForkLineage(targetRoot, forkId) {
|
|
|
24272
25022
|
if (typeof forkId !== "string" || forkId.length === 0 || forkId.length > 64 || !CAPSULE_ID_PATTERN.test(forkId)) {
|
|
24273
25023
|
return null;
|
|
24274
25024
|
}
|
|
24275
|
-
const rootAbs =
|
|
24276
|
-
const rootReal = await
|
|
24277
|
-
const lineagePath =
|
|
24278
|
-
const rel =
|
|
24279
|
-
if (rel.startsWith("..") ||
|
|
25025
|
+
const rootAbs = path33.resolve(targetRoot);
|
|
25026
|
+
const rootReal = await realpath3(rootAbs).catch(() => rootAbs);
|
|
25027
|
+
const lineagePath = path33.join(rootReal, "forks", forkId, "lineage.json");
|
|
25028
|
+
const rel = path33.relative(rootReal, lineagePath);
|
|
25029
|
+
if (rel.startsWith("..") || path33.isAbsolute(rel)) {
|
|
24280
25030
|
return null;
|
|
24281
25031
|
}
|
|
24282
25032
|
if (!await isLineagePathContained(rootReal, lineagePath)) {
|
|
@@ -24311,25 +25061,25 @@ function validateForkId(forkId) {
|
|
|
24311
25061
|
}
|
|
24312
25062
|
}
|
|
24313
25063
|
async function pathEntryExists(absPath) {
|
|
24314
|
-
const st = await
|
|
25064
|
+
const st = await lstat4(absPath).catch(() => null);
|
|
24315
25065
|
return st !== null;
|
|
24316
25066
|
}
|
|
24317
25067
|
async function isLineagePathContained(rootReal, lineagePath) {
|
|
24318
25068
|
let existing = lineagePath;
|
|
24319
25069
|
const suffix = [];
|
|
24320
|
-
while (existing !==
|
|
24321
|
-
const st = await
|
|
25070
|
+
while (existing !== path33.dirname(existing)) {
|
|
25071
|
+
const st = await lstat4(existing).catch(() => null);
|
|
24322
25072
|
if (st !== null) break;
|
|
24323
|
-
suffix.unshift(
|
|
24324
|
-
existing =
|
|
25073
|
+
suffix.unshift(path33.basename(existing));
|
|
25074
|
+
existing = path33.dirname(existing);
|
|
24325
25075
|
}
|
|
24326
|
-
const existingReal = await
|
|
24327
|
-
const targetReal = suffix.length > 0 ?
|
|
24328
|
-
const rel =
|
|
25076
|
+
const existingReal = await realpath3(existing).catch(() => existing);
|
|
25077
|
+
const targetReal = suffix.length > 0 ? path33.join(existingReal, ...suffix) : existingReal;
|
|
25078
|
+
const rel = path33.relative(rootReal, targetReal);
|
|
24329
25079
|
if (rel === "") return true;
|
|
24330
25080
|
if (rel === "..") return false;
|
|
24331
|
-
if (rel.startsWith(`..${
|
|
24332
|
-
if (
|
|
25081
|
+
if (rel.startsWith(`..${path33.sep}`)) return false;
|
|
25082
|
+
if (path33.isAbsolute(rel)) return false;
|
|
24333
25083
|
return true;
|
|
24334
25084
|
}
|
|
24335
25085
|
|
|
@@ -24448,4 +25198,4 @@ export {
|
|
|
24448
25198
|
blendGraphExpandedRecallScore,
|
|
24449
25199
|
Orchestrator
|
|
24450
25200
|
};
|
|
24451
|
-
//# sourceMappingURL=chunk-
|
|
25201
|
+
//# sourceMappingURL=chunk-ZHY5TMJG.js.map
|