@remnic/core 9.3.690 → 9.3.692
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-boundary.d.ts +7 -6
- package/dist/access-boundary.js +21 -21
- package/dist/access-cli.js +49 -47
- package/dist/access-cli.js.map +1 -1
- package/dist/access-http.d.ts +7 -6
- package/dist/access-http.js +26 -26
- package/dist/access-mcp.d.ts +7 -6
- package/dist/access-mcp.js +23 -23
- package/dist/access-operations.d.ts +7 -6
- package/dist/access-operations.js +22 -22
- package/dist/{access-service-Dujr3MTm.d.ts → access-service-DvApf9LZ.d.ts} +2 -2
- package/dist/access-service.d.ts +7 -6
- package/dist/access-service.js +20 -20
- package/dist/access-surface-catalog.d.ts +7 -6
- package/dist/action-confidence.d.ts +1 -1
- package/dist/active-memory-bridge.d.ts +1 -1
- package/dist/active-recall.d.ts +1 -1
- package/dist/active-recall.js +1 -1
- package/dist/adapters/index.js +4 -4
- package/dist/adapters/registry.js +2 -2
- package/dist/{auto-sync-NUQWSFQD.js → auto-sync-RWXT6P5M.js} +5 -5
- package/dist/behavior-learner.d.ts +1 -1
- package/dist/behavior-signals.d.ts +1 -1
- package/dist/bootstrap.d.ts +6 -5
- package/dist/briefing.d.ts +1 -1
- package/dist/briefing.js +5 -5
- package/dist/buffer-surprise-report.d.ts +1 -1
- package/dist/buffer.d.ts +1 -1
- package/dist/calibration.d.ts +1 -1
- package/dist/calibration.js +2 -2
- package/dist/capabilities.d.ts +1 -1
- package/dist/{catalog-CKPtJ114.d.ts → catalog-BEWLjdOr.d.ts} +1 -1
- package/dist/causal-behavior.d.ts +1 -1
- package/dist/causal-consolidation.d.ts +1 -1
- package/dist/causal-consolidation.js +8 -8
- package/dist/{chunk-GTDH3IUH.js → chunk-2D27ODNX.js} +2 -2
- package/dist/{chunk-46URPRE6.js → chunk-2EN5WZQB.js} +2 -2
- package/dist/{chunk-3K37VPM3.js → chunk-3BRA3N5A.js} +2 -2
- package/dist/{chunk-RTFAZOIR.js → chunk-3VVH6ZQW.js} +2 -2
- package/dist/{chunk-ZU7N3S6V.js → chunk-4IQNAOP3.js} +6 -142
- package/dist/chunk-4IQNAOP3.js.map +1 -0
- package/dist/{chunk-FIVDN2SM.js → chunk-4RGWCRIJ.js} +4 -4
- package/dist/{chunk-AGJH5ISO.js → chunk-5KBNNUXS.js} +2 -2
- package/dist/{chunk-X7RLU5CR.js → chunk-66HROLW5.js} +2 -2
- package/dist/chunk-6C2BMUZA.js +444 -0
- package/dist/chunk-6C2BMUZA.js.map +1 -0
- package/dist/{chunk-TYF3D4MS.js → chunk-6ZNIUGXB.js} +11 -11
- package/dist/{chunk-UPIBE2DK.js → chunk-ADUAF5EV.js} +2 -2
- package/dist/{chunk-LLONI6PY.js → chunk-AFWEUTMS.js} +2 -2
- package/dist/{chunk-ZUDM75KG.js → chunk-DCWIQFNA.js} +4 -4
- package/dist/{chunk-OMKUJTVJ.js → chunk-DO7MDZMU.js} +4 -4
- package/dist/{chunk-NGFEWFNK.js → chunk-DQHZA7Y3.js} +1 -1
- package/dist/chunk-DQHZA7Y3.js.map +1 -0
- package/dist/{chunk-LXIEXSHU.js → chunk-E6BOD3UJ.js} +2 -2
- package/dist/{chunk-OBXTMFZQ.js → chunk-ECZPWSB5.js} +2 -2
- package/dist/{chunk-CWE74HRG.js → chunk-FM7KLRKN.js} +3 -3
- package/dist/{chunk-BFVPIKDY.js → chunk-GCOSQBQ2.js} +3 -3
- package/dist/chunk-HXNMDPHN.js +149 -0
- package/dist/chunk-HXNMDPHN.js.map +1 -0
- package/dist/{chunk-MDYG7VI7.js → chunk-IREVVFTM.js} +10 -1
- package/dist/{chunk-MDYG7VI7.js.map → chunk-IREVVFTM.js.map} +1 -1
- package/dist/{chunk-RKNJBZ55.js → chunk-JBPKEARU.js} +4 -4
- package/dist/{chunk-CP2NZQLT.js → chunk-KYH53EFD.js} +6 -6
- package/dist/{chunk-LQ6JI4VH.js → chunk-LD53WPMU.js} +4 -4
- package/dist/{chunk-SB6CQTKP.js → chunk-MCV2DD6F.js} +2 -2
- package/dist/{chunk-3FC6LW6T.js → chunk-MRFVMSTR.js} +2 -2
- package/dist/{chunk-WDXCNJSF.js → chunk-MXZWKOOR.js} +2 -2
- package/dist/{chunk-NSVXK7M5.js → chunk-NEILAC3H.js} +3 -3
- package/dist/{chunk-RGNEARXW.js → chunk-NUZ3N445.js} +7 -7
- package/dist/{chunk-WROKD3XC.js → chunk-O4ZIV62T.js} +35 -35
- package/dist/{chunk-PHZKALOE.js → chunk-QFG23CRE.js} +2 -2
- package/dist/{chunk-A4HH2EWA.js → chunk-QVG4LAQO.js} +2 -2
- package/dist/{chunk-54PVJDO5.js → chunk-SAC5V6JT.js} +2 -2
- package/dist/{chunk-XKUKJIOY.js → chunk-SEK4XIDN.js} +6 -6
- package/dist/{chunk-5CEJH5ZN.js → chunk-TAPSNIMA.js} +4 -4
- package/dist/{chunk-2N6UNJSX.js → chunk-U2OBZSGG.js} +2 -2
- package/dist/{chunk-BKAMHZYR.js → chunk-UOCLRM74.js} +2 -2
- package/dist/{chunk-A7UZR6RA.js → chunk-UTUYAPLY.js} +14 -1
- package/dist/chunk-UTUYAPLY.js.map +1 -0
- package/dist/{chunk-Z7KILAOU.js → chunk-V56S3A23.js} +19 -19
- package/dist/{chunk-CUNTLEJP.js → chunk-VFVG4NS2.js} +30 -9
- package/dist/chunk-VFVG4NS2.js.map +1 -0
- package/dist/{chunk-UD5OKH4J.js → chunk-W4ELOUNX.js} +2 -2
- package/dist/{chunk-CE6CBRCV.js → chunk-W4MICQIZ.js} +89 -407
- package/dist/chunk-W4MICQIZ.js.map +1 -0
- package/dist/{chunk-GR77Z2BM.js → chunk-WIKNVFBS.js} +2 -2
- package/dist/{chunk-WRFKZEO6.js → chunk-YQGHW5ML.js} +4 -4
- package/dist/{chunk-67MMWC74.js → chunk-ZLXGFAML.js} +2 -2
- package/dist/{cli-BkDp6WNi.d.ts → cli-BjsY9Le7.d.ts} +3 -3
- package/dist/cli.d.ts +8 -7
- package/dist/cli.js +45 -44
- package/dist/compounding/engine.d.ts +1 -1
- package/dist/compounding/engine.js +5 -5
- package/dist/compounding/preference-consolidator.d.ts +1 -1
- package/dist/compression-optimizer.d.ts +1 -1
- package/dist/config.d.ts +1 -1
- package/dist/config.js +1 -1
- package/dist/connectors/codex-materialize-runner.d.ts +1 -1
- package/dist/connectors/codex-materialize-runner.js +5 -5
- package/dist/connectors/codex-materialize.d.ts +1 -1
- package/dist/connectors/index.d.ts +1 -1
- package/dist/connectors/index.js +5 -5
- package/dist/consolidation-provenance-check.d.ts +1 -1
- package/dist/consolidation-undo.d.ts +1 -1
- package/dist/contradiction/index.d.ts +1 -1
- package/dist/conversation-index/backend.d.ts +1 -1
- package/dist/conversation-index/backend.js +2 -2
- package/dist/conversation-index/chunker.d.ts +1 -1
- package/dist/conversation-index/faiss-adapter.d.ts +1 -1
- package/dist/conversation-index/indexer.d.ts +1 -1
- package/dist/conversation-index/search.d.ts +1 -1
- package/dist/day-summary.d.ts +1 -1
- package/dist/delinearize.d.ts +1 -1
- package/dist/direct-answer-wiring.d.ts +1 -1
- package/dist/direct-answer.d.ts +1 -1
- package/dist/embedding-fallback.d.ts +1 -1
- package/dist/enrichment/index.d.ts +1 -1
- package/dist/entity-retrieval.d.ts +1 -1
- package/dist/entity-retrieval.js +5 -5
- package/dist/entity-schema.d.ts +1 -1
- package/dist/event-time.d.ts +35 -0
- package/dist/event-time.js +325 -0
- package/dist/event-time.js.map +1 -0
- package/dist/explicit-capture.d.ts +6 -5
- package/dist/extraction-judge-telemetry.d.ts +1 -1
- package/dist/extraction-judge-training.d.ts +1 -1
- package/dist/extraction-judge.d.ts +1 -1
- package/dist/extraction-judge.js +3 -3
- package/dist/extraction.d.ts +1 -1
- package/dist/extraction.js +3 -3
- package/dist/fallback-llm.d.ts +1 -1
- package/dist/fallback-llm.js +2 -2
- package/dist/identity-continuity.d.ts +1 -1
- package/dist/importance.d.ts +1 -1
- package/dist/index.d.ts +11 -10
- package/dist/index.js +77 -75
- package/dist/index.js.map +1 -1
- package/dist/intent.d.ts +1 -1
- package/dist/lcm/engine.d.ts +1 -1
- package/dist/lcm/index.d.ts +1 -1
- package/dist/lcm/tools.d.ts +1 -1
- package/dist/lifecycle.d.ts +1 -1
- package/dist/live-connectors-runner.d.ts +1 -1
- package/dist/local-llm.d.ts +1 -1
- package/dist/maintenance/memory-governance.d.ts +1 -1
- package/dist/maintenance/memory-governance.js +5 -5
- package/dist/maintenance/rebuild-memory-lifecycle-ledger.js +5 -5
- package/dist/maintenance/rebuild-memory-projection.js +6 -6
- package/dist/mcp-memory-inspector-app.d.ts +7 -6
- package/dist/memory-action-policy.d.ts +1 -1
- package/dist/memory-cache.d.ts +1 -1
- package/dist/memory-lifecycle-ledger-utils.d.ts +1 -1
- package/dist/memory-projection-store.d.ts +1 -1
- package/dist/memory-provenance.d.ts +1 -1
- package/dist/memory-worth-outcomes.d.ts +1 -1
- package/dist/models-json.d.ts +1 -1
- package/dist/namespaces/migrate.d.ts +2 -2
- package/dist/namespaces/migrate.js +15 -15
- package/dist/namespaces/principal.d.ts +1 -1
- package/dist/namespaces/search.d.ts +1 -1
- package/dist/namespaces/search.js +9 -9
- package/dist/namespaces/storage.d.ts +2 -2
- package/dist/namespaces/storage.js +5 -5
- package/dist/native-knowledge.d.ts +1 -1
- package/dist/operator-toolkit.d.ts +1 -1
- package/dist/operator-toolkit.js +20 -19
- package/dist/orchestration/maintenance.d.ts +112 -0
- package/dist/orchestration/maintenance.js +39 -0
- package/dist/orchestration/maintenance.js.map +1 -0
- package/dist/{orchestrator-B7ixmUkP.d.ts → orchestrator-CNJCYjZ1.d.ts} +12 -36
- package/dist/orchestrator.d.ts +5 -4
- package/dist/orchestrator.js +42 -40
- package/dist/patterns-cli.d.ts +1 -1
- package/dist/policy-runtime.d.ts +1 -1
- package/dist/provenance.d.ts +1 -1
- package/dist/qmd-recall-cache.d.ts +1 -1
- package/dist/qmd.d.ts +1 -1
- package/dist/recall-disclosure-escalation.d.ts +1 -1
- package/dist/recall-explain-renderer.d.ts +1 -1
- package/dist/recall-explain-renderer.js +3 -3
- package/dist/recall-planner-llm.d.ts +1 -1
- package/dist/recall-planner-llm.js +2 -2
- package/dist/recall-state.d.ts +1 -1
- package/dist/recall-tag-filter.d.ts +1 -1
- package/dist/recall-xray-cli.d.ts +1 -1
- package/dist/recall-xray-cli.js +4 -4
- package/dist/recall-xray-renderer.d.ts +1 -1
- package/dist/recall-xray-renderer.js +3 -3
- package/dist/recall-xray.d.ts +1 -1
- package/dist/recall-xray.js +2 -2
- package/dist/resolve-auth-token.d.ts +1 -1
- package/dist/resume-bundles.js +2 -2
- package/dist/retrieval-agents.d.ts +1 -1
- package/dist/retrieval-tiers.d.ts +1 -1
- package/dist/routing/engine.d.ts +1 -1
- package/dist/routing/store.d.ts +1 -1
- package/dist/search/embed-helper.d.ts +1 -1
- package/dist/search/factory.d.ts +1 -1
- package/dist/search/factory.js +8 -8
- package/dist/search/index.d.ts +1 -1
- package/dist/search/index.js +13 -13
- package/dist/search/lancedb-backend.d.ts +1 -1
- package/dist/search/lancedb-backend.js +2 -2
- package/dist/search/meilisearch-backend.d.ts +1 -1
- package/dist/search/meilisearch-backend.js +2 -2
- package/dist/search/noop-backend.d.ts +1 -1
- package/dist/search/orama-backend.d.ts +1 -1
- package/dist/search/orama-backend.js +2 -2
- package/dist/search/port.d.ts +1 -1
- package/dist/search/remote-backend.d.ts +1 -1
- package/dist/{semantic-consolidation-CWch5uM7.d.ts → semantic-consolidation-D5U0Mrdb.d.ts} +1 -1
- package/dist/semantic-consolidation.d.ts +2 -2
- package/dist/semantic-consolidation.js +6 -6
- package/dist/semantic-rule-promotion.js +5 -5
- package/dist/semantic-rule-verifier.d.ts +1 -1
- package/dist/semantic-rule-verifier.js +5 -5
- package/dist/session-observer-bands.d.ts +1 -1
- package/dist/session-observer-state.d.ts +1 -1
- package/dist/shared-context/manager.d.ts +1 -1
- package/dist/signal.d.ts +1 -1
- package/dist/storage.d.ts +3 -1
- package/dist/storage.js +4 -4
- package/dist/summarizer.d.ts +1 -1
- package/dist/summarizer.js +3 -3
- package/dist/summary-snapshot.d.ts +1 -1
- package/dist/temporal-supersession.d.ts +1 -1
- package/dist/temporal-supersession.js +2 -2
- package/dist/temporal-validity.d.ts +22 -2
- package/dist/temporal-validity.js +3 -1
- package/dist/threading.d.ts +1 -1
- package/dist/tier-migration.d.ts +1 -1
- package/dist/tier-routing.d.ts +1 -1
- package/dist/topics.d.ts +1 -1
- package/dist/transcript.d.ts +1 -1
- package/dist/{types-Dm5xxVrr.d.ts → types-2NoBoRBM.d.ts} +38 -0
- package/dist/types.d.ts +1 -1
- package/dist/types.js +1 -1
- package/dist/utility-runtime.d.ts +1 -1
- package/dist/verified-recall.js +5 -5
- package/package.json +12 -2
- package/src/bitemporal-frontmatter.test.ts +177 -0
- package/src/config.ts +13 -0
- package/src/event-time.test.ts +514 -0
- package/src/event-time.ts +548 -0
- package/src/orchestration/maintenance.test.ts +738 -0
- package/src/orchestration/maintenance.ts +557 -0
- package/src/orchestrator-flush.test.ts +0 -599
- package/src/orchestrator.ts +60 -420
- package/src/storage.ts +34 -0
- package/src/temporal-validity.ts +34 -0
- package/src/types.ts +38 -0
- package/dist/chunk-A7UZR6RA.js.map +0 -1
- package/dist/chunk-CE6CBRCV.js.map +0 -1
- package/dist/chunk-CUNTLEJP.js.map +0 -1
- package/dist/chunk-NGFEWFNK.js.map +0 -1
- package/dist/chunk-ZU7N3S6V.js.map +0 -1
- /package/dist/{auto-sync-NUQWSFQD.js.map → auto-sync-RWXT6P5M.js.map} +0 -0
- /package/dist/{chunk-GTDH3IUH.js.map → chunk-2D27ODNX.js.map} +0 -0
- /package/dist/{chunk-46URPRE6.js.map → chunk-2EN5WZQB.js.map} +0 -0
- /package/dist/{chunk-3K37VPM3.js.map → chunk-3BRA3N5A.js.map} +0 -0
- /package/dist/{chunk-RTFAZOIR.js.map → chunk-3VVH6ZQW.js.map} +0 -0
- /package/dist/{chunk-FIVDN2SM.js.map → chunk-4RGWCRIJ.js.map} +0 -0
- /package/dist/{chunk-AGJH5ISO.js.map → chunk-5KBNNUXS.js.map} +0 -0
- /package/dist/{chunk-X7RLU5CR.js.map → chunk-66HROLW5.js.map} +0 -0
- /package/dist/{chunk-TYF3D4MS.js.map → chunk-6ZNIUGXB.js.map} +0 -0
- /package/dist/{chunk-UPIBE2DK.js.map → chunk-ADUAF5EV.js.map} +0 -0
- /package/dist/{chunk-LLONI6PY.js.map → chunk-AFWEUTMS.js.map} +0 -0
- /package/dist/{chunk-ZUDM75KG.js.map → chunk-DCWIQFNA.js.map} +0 -0
- /package/dist/{chunk-OMKUJTVJ.js.map → chunk-DO7MDZMU.js.map} +0 -0
- /package/dist/{chunk-LXIEXSHU.js.map → chunk-E6BOD3UJ.js.map} +0 -0
- /package/dist/{chunk-OBXTMFZQ.js.map → chunk-ECZPWSB5.js.map} +0 -0
- /package/dist/{chunk-CWE74HRG.js.map → chunk-FM7KLRKN.js.map} +0 -0
- /package/dist/{chunk-BFVPIKDY.js.map → chunk-GCOSQBQ2.js.map} +0 -0
- /package/dist/{chunk-RKNJBZ55.js.map → chunk-JBPKEARU.js.map} +0 -0
- /package/dist/{chunk-CP2NZQLT.js.map → chunk-KYH53EFD.js.map} +0 -0
- /package/dist/{chunk-LQ6JI4VH.js.map → chunk-LD53WPMU.js.map} +0 -0
- /package/dist/{chunk-SB6CQTKP.js.map → chunk-MCV2DD6F.js.map} +0 -0
- /package/dist/{chunk-3FC6LW6T.js.map → chunk-MRFVMSTR.js.map} +0 -0
- /package/dist/{chunk-WDXCNJSF.js.map → chunk-MXZWKOOR.js.map} +0 -0
- /package/dist/{chunk-NSVXK7M5.js.map → chunk-NEILAC3H.js.map} +0 -0
- /package/dist/{chunk-RGNEARXW.js.map → chunk-NUZ3N445.js.map} +0 -0
- /package/dist/{chunk-WROKD3XC.js.map → chunk-O4ZIV62T.js.map} +0 -0
- /package/dist/{chunk-PHZKALOE.js.map → chunk-QFG23CRE.js.map} +0 -0
- /package/dist/{chunk-A4HH2EWA.js.map → chunk-QVG4LAQO.js.map} +0 -0
- /package/dist/{chunk-54PVJDO5.js.map → chunk-SAC5V6JT.js.map} +0 -0
- /package/dist/{chunk-XKUKJIOY.js.map → chunk-SEK4XIDN.js.map} +0 -0
- /package/dist/{chunk-5CEJH5ZN.js.map → chunk-TAPSNIMA.js.map} +0 -0
- /package/dist/{chunk-2N6UNJSX.js.map → chunk-U2OBZSGG.js.map} +0 -0
- /package/dist/{chunk-BKAMHZYR.js.map → chunk-UOCLRM74.js.map} +0 -0
- /package/dist/{chunk-Z7KILAOU.js.map → chunk-V56S3A23.js.map} +0 -0
- /package/dist/{chunk-UD5OKH4J.js.map → chunk-W4ELOUNX.js.map} +0 -0
- /package/dist/{chunk-GR77Z2BM.js.map → chunk-WIKNVFBS.js.map} +0 -0
- /package/dist/{chunk-WRFKZEO6.js.map → chunk-YQGHW5ML.js.map} +0 -0
- /package/dist/{chunk-67MMWC74.js.map → chunk-ZLXGFAML.js.map} +0 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@remnic/core",
|
|
3
|
-
"version": "9.3.
|
|
3
|
+
"version": "9.3.692",
|
|
4
4
|
"description": "Framework-agnostic Remnic memory engine — orchestrator, storage, extraction, search, trust zones",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -1646,6 +1646,16 @@
|
|
|
1646
1646
|
"remnic-source": "./src/orchestrator.ts",
|
|
1647
1647
|
"import": "./dist/orchestrator.js"
|
|
1648
1648
|
},
|
|
1649
|
+
"./orchestration/maintenance": {
|
|
1650
|
+
"types": "./dist/orchestration/maintenance.d.ts",
|
|
1651
|
+
"remnic-source": "./src/orchestration/maintenance.ts",
|
|
1652
|
+
"import": "./dist/orchestration/maintenance.js"
|
|
1653
|
+
},
|
|
1654
|
+
"./orchestration/maintenance.js": {
|
|
1655
|
+
"types": "./dist/orchestration/maintenance.d.ts",
|
|
1656
|
+
"remnic-source": "./src/orchestration/maintenance.ts",
|
|
1657
|
+
"import": "./dist/orchestration/maintenance.js"
|
|
1658
|
+
},
|
|
1649
1659
|
"./page-versioning": {
|
|
1650
1660
|
"types": "./dist/page-versioning.d.ts",
|
|
1651
1661
|
"remnic-source": "./src/page-versioning.ts",
|
|
@@ -2931,7 +2941,7 @@
|
|
|
2931
2941
|
"core"
|
|
2932
2942
|
],
|
|
2933
2943
|
"peerDependencies": {
|
|
2934
|
-
"@remnic/coding-graph": "^9.3.
|
|
2944
|
+
"@remnic/coding-graph": "^9.3.692"
|
|
2935
2945
|
},
|
|
2936
2946
|
"peerDependenciesMeta": {
|
|
2937
2947
|
"@remnic/coding-graph": {
|
|
@@ -0,0 +1,177 @@
|
|
|
1
|
+
import test from "node:test";
|
|
2
|
+
import assert from "node:assert/strict";
|
|
3
|
+
import os from "node:os";
|
|
4
|
+
import path from "node:path";
|
|
5
|
+
import { mkdtemp, rm } from "node:fs/promises";
|
|
6
|
+
|
|
7
|
+
import { StorageManager } from "./storage.js";
|
|
8
|
+
import { isValidityExpiredNow } from "./temporal-validity.js";
|
|
9
|
+
|
|
10
|
+
/**
|
|
11
|
+
* Issue #1578 PR 1 — bi-temporal validity frontmatter round-trip + injection
|
|
12
|
+
* filter unit tests.
|
|
13
|
+
*
|
|
14
|
+
* These tests pin the on-disk contract added by #1578 (`observedAt`,
|
|
15
|
+
* `eventTimeSource`) AND prove the pre-existing temporal/lifecycle fields
|
|
16
|
+
* (`created`, `updated`, `source`, `valid_at`, `invalid_at`, `forgottenAt`)
|
|
17
|
+
* round-trip unchanged alongside them — i.e. the parser was not corrupted by
|
|
18
|
+
* the additive change. Every test goes through the public StorageManager API
|
|
19
|
+
* (`writeMemory` + `writeMemoryFrontmatter`, both of which route through the
|
|
20
|
+
* `serializeFrontmatter` chokepoint) so the serialize → parse round trip is
|
|
21
|
+
* exercised end to end.
|
|
22
|
+
*
|
|
23
|
+
* The injection filter (`isValidityExpiredNow`) is a pure function, so it is
|
|
24
|
+
* unit-tested directly with minimal frontmatter fragments.
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
const OBSERVED = "2026-06-20T14:02:11.000Z";
|
|
28
|
+
const VALID_FROM = "2026-03-01T00:00:00.000Z";
|
|
29
|
+
const VALID_UNTIL = "2026-06-15T00:00:00.000Z";
|
|
30
|
+
|
|
31
|
+
test("round-trip: observedAt + eventTimeSource + valid_at survive write → readAllMemories", async () => {
|
|
32
|
+
const dir = await mkdtemp(path.join(os.tmpdir(), "remnic-bitemporal-rt-"));
|
|
33
|
+
try {
|
|
34
|
+
const storage = new StorageManager(dir);
|
|
35
|
+
await storage.ensureDirectories();
|
|
36
|
+
|
|
37
|
+
const id = await storage.writeMemory("fact", "We moved offices in March.", {
|
|
38
|
+
observedAt: OBSERVED,
|
|
39
|
+
eventTimeSource: "extracted",
|
|
40
|
+
validAt: VALID_FROM,
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
const memories = await storage.readAllMemories();
|
|
44
|
+
const written = memories.find((m) => m.frontmatter.id === id);
|
|
45
|
+
assert.ok(written, "fact must be discoverable after write");
|
|
46
|
+
assert.equal(written!.frontmatter.observedAt, OBSERVED);
|
|
47
|
+
assert.equal(written!.frontmatter.eventTimeSource, "extracted");
|
|
48
|
+
assert.equal(written!.frontmatter.valid_at, VALID_FROM);
|
|
49
|
+
// The auto-set baseline fields must remain present and well-formed.
|
|
50
|
+
assert.ok(typeof written!.frontmatter.created === "string" && written!.frontmatter.created!.length > 0);
|
|
51
|
+
assert.ok(typeof written!.frontmatter.updated === "string" && written!.frontmatter.updated!.length > 0);
|
|
52
|
+
assert.equal(written!.frontmatter.source, "extraction");
|
|
53
|
+
} finally {
|
|
54
|
+
await rm(dir, { recursive: true, force: true });
|
|
55
|
+
}
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
test("round-trip: invalid_at + forgottenAt coexist with observedAt/eventTimeSource (parser not corrupted)", async () => {
|
|
59
|
+
// Exercises the full serialize→parse round trip through the
|
|
60
|
+
// writeMemoryFrontmatter chokepoint for the fields writeMemory does not
|
|
61
|
+
// accept as options (invalid_at, forgottenAt). This is the direct
|
|
62
|
+
// regression guard for the "frontmatter parser corruption" risk: every
|
|
63
|
+
// pre-existing field must survive alongside the new bi-temporal fields,
|
|
64
|
+
// with no field dropped or duplicated.
|
|
65
|
+
const dir = await mkdtemp(path.join(os.tmpdir(), "remnic-bitemporal-coexist-"));
|
|
66
|
+
try {
|
|
67
|
+
const storage = new StorageManager(dir);
|
|
68
|
+
await storage.ensureDirectories();
|
|
69
|
+
|
|
70
|
+
const id = await storage.writeMemory("fact", "Old stack was Node 18.", {
|
|
71
|
+
observedAt: OBSERVED,
|
|
72
|
+
eventTimeSource: "assumed",
|
|
73
|
+
validAt: VALID_FROM,
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
const before = await storage.readAllMemories();
|
|
77
|
+
const memory = before.find((m) => m.frontmatter.id === id);
|
|
78
|
+
assert.ok(memory);
|
|
79
|
+
|
|
80
|
+
const ok = await storage.writeMemoryFrontmatter(memory!, {
|
|
81
|
+
invalid_at: VALID_UNTIL,
|
|
82
|
+
forgottenAt: "2026-07-01T00:00:00.000Z",
|
|
83
|
+
});
|
|
84
|
+
assert.equal(ok, true);
|
|
85
|
+
|
|
86
|
+
const after = await storage.readAllMemories();
|
|
87
|
+
const patched = after.find((m) => m.frontmatter.id === id);
|
|
88
|
+
assert.ok(patched, "patched fact must be readable");
|
|
89
|
+
const fm = patched!.frontmatter;
|
|
90
|
+
// New bi-temporal fields.
|
|
91
|
+
assert.equal(fm.observedAt, OBSERVED);
|
|
92
|
+
assert.equal(fm.eventTimeSource, "assumed");
|
|
93
|
+
// Pre-existing temporal/lifecycle fields — all present, correct values.
|
|
94
|
+
assert.equal(fm.valid_at, VALID_FROM);
|
|
95
|
+
assert.equal(fm.invalid_at, VALID_UNTIL);
|
|
96
|
+
assert.equal(fm.forgottenAt, "2026-07-01T00:00:00.000Z");
|
|
97
|
+
// Baseline identity fields untouched by the patch.
|
|
98
|
+
assert.ok(typeof fm.created === "string" && fm.created!.length > 0);
|
|
99
|
+
assert.ok(typeof fm.source === "string" && fm.source!.length > 0);
|
|
100
|
+
} finally {
|
|
101
|
+
await rm(dir, { recursive: true, force: true });
|
|
102
|
+
}
|
|
103
|
+
});
|
|
104
|
+
|
|
105
|
+
test("legacy memory without bi-temporal fields reads cleanly — observedAt/eventTimeSource undefined", async () => {
|
|
106
|
+
const dir = await mkdtemp(path.join(os.tmpdir(), "remnic-bitemporal-legacy-"));
|
|
107
|
+
try {
|
|
108
|
+
const storage = new StorageManager(dir);
|
|
109
|
+
await storage.ensureDirectories();
|
|
110
|
+
|
|
111
|
+
const id = await storage.writeMemory("fact", "Legacy fact pre-dating #1578.");
|
|
112
|
+
|
|
113
|
+
const memories = await storage.readAllMemories();
|
|
114
|
+
const written = memories.find((m) => m.frontmatter.id === id);
|
|
115
|
+
assert.ok(written);
|
|
116
|
+
assert.equal(written!.frontmatter.observedAt, undefined);
|
|
117
|
+
assert.equal(written!.frontmatter.eventTimeSource, undefined);
|
|
118
|
+
} finally {
|
|
119
|
+
await rm(dir, { recursive: true, force: true });
|
|
120
|
+
}
|
|
121
|
+
});
|
|
122
|
+
|
|
123
|
+
test("garbage observedAt is rejected on write — corrupt timestamps cannot leak to disk", async () => {
|
|
124
|
+
const dir = await mkdtemp(path.join(os.tmpdir(), "remnic-bitemporal-reject-"));
|
|
125
|
+
try {
|
|
126
|
+
const storage = new StorageManager(dir);
|
|
127
|
+
await storage.ensureDirectories();
|
|
128
|
+
|
|
129
|
+
await assert.rejects(
|
|
130
|
+
() => storage.writeMemory("fact", "Bad observedAt.", { observedAt: "not-a-timestamp" }),
|
|
131
|
+
/observedAt must be a valid ISO timestamp/,
|
|
132
|
+
);
|
|
133
|
+
} finally {
|
|
134
|
+
await rm(dir, { recursive: true, force: true });
|
|
135
|
+
}
|
|
136
|
+
});
|
|
137
|
+
|
|
138
|
+
test("isValidityExpiredNow: absent invalid_at → never expired (still valid)", () => {
|
|
139
|
+
assert.equal(isValidityExpiredNow({ invalid_at: undefined }, Date.now()), false);
|
|
140
|
+
assert.equal(isValidityExpiredNow({ invalid_at: "" }, Date.now()), false);
|
|
141
|
+
});
|
|
142
|
+
|
|
143
|
+
test("isValidityExpiredNow: invalid_at in the past → expired (interval ended)", () => {
|
|
144
|
+
const now = Date.parse("2026-06-20T00:00:00.000Z");
|
|
145
|
+
assert.equal(
|
|
146
|
+
isValidityExpiredNow({ invalid_at: "2026-06-15T00:00:00.000Z" }, now),
|
|
147
|
+
true,
|
|
148
|
+
);
|
|
149
|
+
});
|
|
150
|
+
|
|
151
|
+
test("isValidityExpiredNow: invalid_at in the future → not expired (still within window)", () => {
|
|
152
|
+
const now = Date.parse("2026-06-20T00:00:00.000Z");
|
|
153
|
+
assert.equal(
|
|
154
|
+
isValidityExpiredNow({ invalid_at: "2026-12-31T00:00:00.000Z" }, now),
|
|
155
|
+
false,
|
|
156
|
+
);
|
|
157
|
+
});
|
|
158
|
+
|
|
159
|
+
test("isValidityExpiredNow: exclusive end — invalid_at == now is EXPIRED ([from, until) ended)", () => {
|
|
160
|
+
const boundary = Date.parse("2026-06-15T00:00:00.000Z");
|
|
161
|
+
// At the exact exclusive boundary the interval has ended.
|
|
162
|
+
assert.equal(
|
|
163
|
+
isValidityExpiredNow({ invalid_at: "2026-06-15T00:00:00.000Z" }, boundary),
|
|
164
|
+
true,
|
|
165
|
+
);
|
|
166
|
+
});
|
|
167
|
+
|
|
168
|
+
test("isValidityExpiredNow: status-orthogonal — considers invalid_at only, ignores status", () => {
|
|
169
|
+
// The filter must be status-orthogonal (issue pitfall matrix): an `active`
|
|
170
|
+
// memory can be validity-expired. isValidityExpiredNow only receives the
|
|
171
|
+
// invalid_at field, so status never enters the decision.
|
|
172
|
+
const now = Date.parse("2026-06-20T00:00:00.000Z");
|
|
173
|
+
assert.equal(
|
|
174
|
+
isValidityExpiredNow({ invalid_at: "2026-06-15T00:00:00.000Z" }, now),
|
|
175
|
+
true,
|
|
176
|
+
);
|
|
177
|
+
});
|
package/src/config.ts
CHANGED
|
@@ -2084,6 +2084,19 @@ export function parseConfig(
|
|
|
2084
2084
|
temporalSupersessionEnabled: cfg.temporalSupersessionEnabled !== false, // On by default
|
|
2085
2085
|
temporalSupersessionIncludeInRecall:
|
|
2086
2086
|
cfg.temporalSupersessionIncludeInRecall === true, // Off by default
|
|
2087
|
+
// Bi-temporal validity (issue #1578). Default `false` so recall behaves
|
|
2088
|
+
// byte-identically to pre-#1578 until an operator opts in. Uses coerceBool
|
|
2089
|
+
// (same as recallDirectAnswerEnabled below) so CLI string "true" works.
|
|
2090
|
+
//
|
|
2091
|
+
// CURRENT scope (this PR): the recall injection filter (expired-validity
|
|
2092
|
+
// facts leave default injection but stay findable by explicit search and
|
|
2093
|
+
// as_of queries) + the observedAt/eventTimeSource storage fields. The
|
|
2094
|
+
// extraction prompt → resolveEventTime write-time wiring lands in a
|
|
2095
|
+
// follow-on PR; until then, enabling the gate exercises the filter and
|
|
2096
|
+
// storage round-trip but new extractions are not yet event-time-resolved
|
|
2097
|
+
// (docs kept honest — review: wire resolver before exposing the gate).
|
|
2098
|
+
temporalBiTemporal: coerceBool(cfg.temporalBiTemporal) ?? false,
|
|
2099
|
+
temporalExpiredInInjection: coerceBool(cfg.temporalExpiredInInjection) ?? false,
|
|
2087
2100
|
// Direct-answer retrieval tier (issue #518). Default off so the
|
|
2088
2101
|
// recall path keeps least-privileged behavior unless operators
|
|
2089
2102
|
// explicitly opt in.
|