@remnic/core 9.3.727 → 9.3.729
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 +2 -2
- package/dist/access-boundary.js +6 -6
- package/dist/access-cli.js +11 -11
- package/dist/access-http.d.ts +2 -2
- package/dist/access-http.js +10 -10
- package/dist/access-mcp.d.ts +2 -2
- package/dist/access-mcp.js +9 -9
- package/dist/access-operations-batch.js +7 -7
- package/dist/access-operations.d.ts +8 -8
- package/dist/access-operations.js +8 -8
- package/dist/access-schema.d.ts +46 -46
- package/dist/{access-service-Bgpjxo4f.d.ts → access-service-BXMJqkTA.d.ts} +1 -1
- package/dist/access-service.d.ts +2 -2
- package/dist/access-service.js +5 -5
- package/dist/access-surface-catalog.d.ts +2 -2
- package/dist/bootstrap.d.ts +1 -1
- package/dist/capabilities.d.ts +43 -1
- package/dist/capabilities.js +5 -3
- package/dist/{chunk-DVRHLN2O.js → chunk-3RCBIOOJ.js} +18 -2
- package/dist/{chunk-DVRHLN2O.js.map → chunk-3RCBIOOJ.js.map} +1 -1
- package/dist/{chunk-R7IYU5DZ.js → chunk-4ESAR77N.js} +2 -2
- package/dist/{chunk-SNKPUJHR.js → chunk-76NHR6ZL.js} +3 -3
- package/dist/{chunk-6PY5YJAV.js → chunk-BQCHEV7O.js} +8 -3
- package/dist/{chunk-6PY5YJAV.js.map → chunk-BQCHEV7O.js.map} +1 -1
- package/dist/{chunk-ZA2S2VLL.js → chunk-C2PG7IEH.js} +5 -2
- package/dist/chunk-C2PG7IEH.js.map +1 -0
- package/dist/{chunk-MJIHJ7OG.js → chunk-H5BWGCRZ.js} +11 -10
- package/dist/chunk-H5BWGCRZ.js.map +1 -0
- package/dist/{chunk-XPHVAOBT.js → chunk-HEDZUSCS.js} +180 -101
- package/dist/chunk-HEDZUSCS.js.map +1 -0
- package/dist/{chunk-N3VNUM4Z.js → chunk-HGNOCPZX.js} +4 -4
- package/dist/{chunk-CSRXQ6NB.js → chunk-I5REUWLH.js} +10 -4
- package/dist/chunk-I5REUWLH.js.map +1 -0
- package/dist/{chunk-NSA5ZRUL.js → chunk-M4AYVEWS.js} +3 -3
- package/dist/{chunk-OEEW4KJA.js → chunk-O6YH5F47.js} +3 -3
- package/dist/{chunk-27QQC7ZX.js → chunk-UM5AWJNQ.js} +6 -5
- package/dist/chunk-UM5AWJNQ.js.map +1 -0
- package/dist/{chunk-2KAYTPPT.js → chunk-UTHQPSRC.js} +2 -2
- package/dist/{chunk-CTOQEZSN.js → chunk-V4GNSDFH.js} +2 -2
- package/dist/{chunk-EHISUJFN.js → chunk-WAS3NV46.js} +6 -3
- package/dist/chunk-WAS3NV46.js.map +1 -0
- package/dist/{chunk-DKJCRGWM.js → chunk-YGIQORJ3.js} +2 -2
- package/dist/{cli-BLME420h.d.ts → cli-DmAiDd8A.d.ts} +2 -2
- package/dist/cli.d.ts +3 -3
- package/dist/cli.js +13 -13
- package/dist/embedding-fallback.js +2 -1
- package/dist/explicit-capture.d.ts +1 -1
- package/dist/extraction.js +2 -1
- package/dist/{first-start-migration-PG5HBC3K.js → first-start-migration-22LPFHD5.js} +6 -2
- package/dist/first-start-migration-22LPFHD5.js.map +1 -0
- package/dist/index.d.ts +4 -4
- package/dist/index.js +16 -16
- package/dist/mcp-memory-inspector-app.d.ts +2 -2
- package/dist/namespaces/migrate.js +5 -4
- package/dist/namespaces/search.js +4 -3
- package/dist/operator-toolkit.js +6 -6
- package/dist/{orchestrator-DqPAz8ot.d.ts → orchestrator-BR0sGsME.d.ts} +104 -26
- package/dist/orchestrator.d.ts +1 -1
- package/dist/orchestrator.js +7 -7
- package/dist/schemas.d.ts +74 -74
- package/dist/search/embed-helper.js +2 -1
- package/dist/search/factory.js +3 -2
- package/dist/search/index.js +3 -2
- package/dist/shared-context/manager.d.ts +2 -2
- package/dist/transfer/types.d.ts +12 -12
- package/package.json +2 -2
- package/src/access-service.ts +2 -1
- package/src/capabilities.test.ts +155 -0
- package/src/capabilities.ts +91 -0
- package/src/chat/chat-engine.test.ts +39 -1
- package/src/chat/chat-session.ts +25 -2
- package/src/cli.ts +3 -2
- package/src/embedding-fallback.ts +2 -1
- package/src/extraction.ts +7 -3
- package/src/maintenance/first-start-migration.ts +3 -1
- package/src/orchestration/extraction-queue-coordinator.ts +175 -0
- package/src/orchestrator-extraction-queue.test.ts +26 -38
- package/src/orchestrator-flush.test.ts +10 -15
- package/src/orchestrator.ts +52 -104
- package/src/search/embed-helper.ts +3 -2
- package/dist/chunk-27QQC7ZX.js.map +0 -1
- package/dist/chunk-CSRXQ6NB.js.map +0 -1
- package/dist/chunk-EHISUJFN.js.map +0 -1
- package/dist/chunk-MJIHJ7OG.js.map +0 -1
- package/dist/chunk-XPHVAOBT.js.map +0 -1
- package/dist/chunk-ZA2S2VLL.js.map +0 -1
- package/dist/first-start-migration-PG5HBC3K.js.map +0 -1
- /package/dist/{chunk-R7IYU5DZ.js.map → chunk-4ESAR77N.js.map} +0 -0
- /package/dist/{chunk-SNKPUJHR.js.map → chunk-76NHR6ZL.js.map} +0 -0
- /package/dist/{chunk-N3VNUM4Z.js.map → chunk-HGNOCPZX.js.map} +0 -0
- /package/dist/{chunk-NSA5ZRUL.js.map → chunk-M4AYVEWS.js.map} +0 -0
- /package/dist/{chunk-OEEW4KJA.js.map → chunk-O6YH5F47.js.map} +0 -0
- /package/dist/{chunk-2KAYTPPT.js.map → chunk-UTHQPSRC.js.map} +0 -0
- /package/dist/{chunk-CTOQEZSN.js.map → chunk-V4GNSDFH.js.map} +0 -0
- /package/dist/{chunk-DKJCRGWM.js.map → chunk-YGIQORJ3.js.map} +0 -0
|
@@ -154,7 +154,7 @@ import {
|
|
|
154
154
|
} from "./chunk-LTHVM4XN.js";
|
|
155
155
|
import {
|
|
156
156
|
ExtractionEngine
|
|
157
|
-
} from "./chunk-
|
|
157
|
+
} from "./chunk-I5REUWLH.js";
|
|
158
158
|
import {
|
|
159
159
|
parseMemoryActionEligibilityContext
|
|
160
160
|
} from "./chunk-5GSUBCZM.js";
|
|
@@ -187,7 +187,7 @@ import {
|
|
|
187
187
|
} from "./chunk-Q6IP2ARR.js";
|
|
188
188
|
import {
|
|
189
189
|
EmbeddingFallback
|
|
190
|
-
} from "./chunk-
|
|
190
|
+
} from "./chunk-C2PG7IEH.js";
|
|
191
191
|
import {
|
|
192
192
|
buildEntityRecallSection,
|
|
193
193
|
entityRecentTranscriptLookbackHours,
|
|
@@ -333,11 +333,11 @@ import {
|
|
|
333
333
|
} from "./chunk-J6BH2OBA.js";
|
|
334
334
|
import {
|
|
335
335
|
NamespaceSearchRouter
|
|
336
|
-
} from "./chunk-
|
|
336
|
+
} from "./chunk-V4GNSDFH.js";
|
|
337
337
|
import {
|
|
338
338
|
createConversationIndexRuntime,
|
|
339
339
|
createSearchBackend
|
|
340
|
-
} from "./chunk-
|
|
340
|
+
} from "./chunk-UTHQPSRC.js";
|
|
341
341
|
import {
|
|
342
342
|
NoopSearchBackend
|
|
343
343
|
} from "./chunk-CYEPCZN5.js";
|
|
@@ -363,8 +363,9 @@ import {
|
|
|
363
363
|
} from "./chunk-EH5ED3C6.js";
|
|
364
364
|
import {
|
|
365
365
|
resolveCapabilities,
|
|
366
|
-
resolveGraphConstructionCapabilities
|
|
367
|
-
|
|
366
|
+
resolveGraphConstructionCapabilities,
|
|
367
|
+
resolveMemoryLifecycleCapabilities
|
|
368
|
+
} from "./chunk-3RCBIOOJ.js";
|
|
368
369
|
import {
|
|
369
370
|
searchCausalTrajectories
|
|
370
371
|
} from "./chunk-SQNED75R.js";
|
|
@@ -745,6 +746,130 @@ var TierMigrationCoordinator = class {
|
|
|
745
746
|
}
|
|
746
747
|
};
|
|
747
748
|
|
|
749
|
+
// src/orchestration/extraction-queue-coordinator.ts
|
|
750
|
+
var ExtractionQueueCoordinator = class {
|
|
751
|
+
/**
|
|
752
|
+
* Background serial queue for extractions (agent_end optimization).
|
|
753
|
+
* Queue stores tasks that resolve when extraction should run.
|
|
754
|
+
*/
|
|
755
|
+
queue = [];
|
|
756
|
+
/** Whether the serial drain loop is currently running. */
|
|
757
|
+
processing = false;
|
|
758
|
+
/** Current queue depth (idle-wait + test seam). */
|
|
759
|
+
get length() {
|
|
760
|
+
return this.queue.length;
|
|
761
|
+
}
|
|
762
|
+
/** Whether the serial drain loop is currently running (idle-wait + test seam). */
|
|
763
|
+
get isProcessing() {
|
|
764
|
+
return this.processing;
|
|
765
|
+
}
|
|
766
|
+
/**
|
|
767
|
+
* Enqueue a task and start the serial processor if it is idle. This is
|
|
768
|
+
* the production entry point — the orchestrator's `queueBufferedExtraction`
|
|
769
|
+
* builds each task closure and hands it here.
|
|
770
|
+
*/
|
|
771
|
+
enqueue(task) {
|
|
772
|
+
this.queue.push(task);
|
|
773
|
+
if (!this.processing) {
|
|
774
|
+
this.processing = true;
|
|
775
|
+
this.processQueue().catch((err) => {
|
|
776
|
+
this.logExtractionQueueFailure(err, "processor");
|
|
777
|
+
this.processing = false;
|
|
778
|
+
});
|
|
779
|
+
}
|
|
780
|
+
}
|
|
781
|
+
/**
|
|
782
|
+
* Background serial queue processor.
|
|
783
|
+
* Processes extractions one at a time to avoid race conditions.
|
|
784
|
+
* Called automatically when items are queued via `enqueue`; also exposed
|
|
785
|
+
* for the characterization tests that push raw tasks and assert drain
|
|
786
|
+
* semantics directly.
|
|
787
|
+
*/
|
|
788
|
+
async processQueue() {
|
|
789
|
+
while (this.queue.length > 0) {
|
|
790
|
+
const task = this.queue.shift();
|
|
791
|
+
if (task) {
|
|
792
|
+
try {
|
|
793
|
+
await task();
|
|
794
|
+
} catch (err) {
|
|
795
|
+
this.logExtractionQueueFailure(err, "task");
|
|
796
|
+
}
|
|
797
|
+
}
|
|
798
|
+
}
|
|
799
|
+
this.processing = false;
|
|
800
|
+
}
|
|
801
|
+
/**
|
|
802
|
+
* Classify + log a failure from either the per-task catch inside
|
|
803
|
+
* `processQueue()` or the outer `processQueue().catch(...)` in
|
|
804
|
+
* `enqueue()`. Issue #549: `throwIfRecallAborted`
|
|
805
|
+
* (used throughout `runExtraction`) raises an Error whose `name` is
|
|
806
|
+
* `"AbortError"`. That path fires when `before_reset` aborts a
|
|
807
|
+
* queued task to avoid duplicate extraction — it is intentional
|
|
808
|
+
* cancellation, not a failure. Downgrading the log to debug
|
|
809
|
+
* prevents spurious `error`-level lines that routinely appear
|
|
810
|
+
* right next to a successful `persisted: N facts, M entities` log
|
|
811
|
+
* and that confuse operators into thinking extraction is broken.
|
|
812
|
+
* Genuine extraction failures (network, parse, I/O) still log at
|
|
813
|
+
* `error`.
|
|
814
|
+
*
|
|
815
|
+
* Source differentiates the two call sites so the log message
|
|
816
|
+
* names the right layer (`task` vs `processor`).
|
|
817
|
+
*/
|
|
818
|
+
logExtractionQueueFailure(err, source) {
|
|
819
|
+
const aborted = source === "task" ? "background extraction task aborted (session transition)" : "background extraction queue processor aborted (session transition)";
|
|
820
|
+
const failed = source === "task" ? "background extraction task failed" : "background extraction queue processor failed";
|
|
821
|
+
if (isAbortError(err)) {
|
|
822
|
+
log.debug(aborted);
|
|
823
|
+
} else {
|
|
824
|
+
log.error(failed, err);
|
|
825
|
+
}
|
|
826
|
+
}
|
|
827
|
+
/**
|
|
828
|
+
* Wait until the extraction queue is fully drained (no tasks queued, no
|
|
829
|
+
* drain in flight) or `timeoutMs` elapses. Used by bootstrap (after a
|
|
830
|
+
* dry-run import) and by tests that need to assert extraction settled.
|
|
831
|
+
* Returns false on timeout, true once idle.
|
|
832
|
+
*/
|
|
833
|
+
async waitForIdle(timeoutMs = 6e4) {
|
|
834
|
+
const started = Date.now();
|
|
835
|
+
while (this.processing || this.queue.length > 0) {
|
|
836
|
+
if (Date.now() - started > timeoutMs) {
|
|
837
|
+
log.warn(`waitForExtractionIdle timed out after ${timeoutMs}ms`);
|
|
838
|
+
return false;
|
|
839
|
+
}
|
|
840
|
+
const { promise, resolve } = Promise.withResolvers();
|
|
841
|
+
setTimeout(resolve, 50);
|
|
842
|
+
await promise;
|
|
843
|
+
}
|
|
844
|
+
return true;
|
|
845
|
+
}
|
|
846
|
+
// ── Test seams ─────────────────────────────────────────────────────────
|
|
847
|
+
// Mirror the pre-extraction `orchestrator.extractionQueue` /
|
|
848
|
+
// `orchestrator.queueProcessing` direct-field access the characterization
|
|
849
|
+
// and flush deadline tests relied on. Each is a thin, well-named handle
|
|
850
|
+
// onto the coordinator's private state — no behavior change.
|
|
851
|
+
/**
|
|
852
|
+
* Push a raw task WITHOUT auto-starting the processor, matching the
|
|
853
|
+
* pre-extraction `this.extractionQueue.push(...)` used by the
|
|
854
|
+
* characterization tests that drive the drain manually via `processQueue`.
|
|
855
|
+
*/
|
|
856
|
+
pushRaw(task) {
|
|
857
|
+
this.queue.push(task);
|
|
858
|
+
}
|
|
859
|
+
/** Remove + return the front task (test seam for the flush deadline tests). */
|
|
860
|
+
shift() {
|
|
861
|
+
return this.queue.shift();
|
|
862
|
+
}
|
|
863
|
+
/**
|
|
864
|
+
* Force the processor-busy flag so `enqueue` does not auto-start the
|
|
865
|
+
* drain — used by the flush deadline test to simulate a busy queue and
|
|
866
|
+
* assert a queued task's deadline expires while it waits.
|
|
867
|
+
*/
|
|
868
|
+
setProcessingForTest(value) {
|
|
869
|
+
this.processing = value;
|
|
870
|
+
}
|
|
871
|
+
};
|
|
872
|
+
|
|
748
873
|
// src/maintenance/pattern-reinforcement.ts
|
|
749
874
|
function patternReinforcementKey(content) {
|
|
750
875
|
return content.trim().toLowerCase().replace(/\s+/g, " ").slice(0, 200);
|
|
@@ -2997,10 +3122,14 @@ var Orchestrator = class _Orchestrator {
|
|
|
2997
3122
|
passiveCorrectionDedup = /* @__PURE__ */ new Set();
|
|
2998
3123
|
_passiveCorrectionService = null;
|
|
2999
3124
|
passiveCorrectionTelemetry = { detected: 0, queued: 0, autoApplied: 0, suppressedReasonCounts: {} };
|
|
3000
|
-
|
|
3001
|
-
|
|
3002
|
-
|
|
3003
|
-
|
|
3125
|
+
/**
|
|
3126
|
+
* Background serial extraction queue coordinator (issue #1526 — moved
|
|
3127
|
+
* from inline `extractionQueue`/`queueProcessing` fields). Owns queue
|
|
3128
|
+
* state + scheduling + the serial drain + failure classification; the
|
|
3129
|
+
* orchestrator builds each task closure in `queueBufferedExtraction` and
|
|
3130
|
+
* hands it to `enqueue`.
|
|
3131
|
+
*/
|
|
3132
|
+
extractionQueueCoordinator;
|
|
3004
3133
|
heartbeatObserverChains = /* @__PURE__ */ new Map();
|
|
3005
3134
|
recentExtractionFingerprints = /* @__PURE__ */ new Map();
|
|
3006
3135
|
consolidationObservers = /* @__PURE__ */ new Set();
|
|
@@ -3705,6 +3834,7 @@ var Orchestrator = class _Orchestrator {
|
|
|
3705
3834
|
namespaceSearchRouter: this.namespaceSearchRouter,
|
|
3706
3835
|
namespaceCatalog: this.namespaceCatalog
|
|
3707
3836
|
});
|
|
3837
|
+
this.extractionQueueCoordinator = new ExtractionQueueCoordinator();
|
|
3708
3838
|
const conversationIndexRuntime = createConversationIndexRuntime(config, {
|
|
3709
3839
|
getQmd: () => this.conversationQmd,
|
|
3710
3840
|
getFaiss: () => this.conversationFaiss
|
|
@@ -3787,8 +3917,9 @@ var Orchestrator = class _Orchestrator {
|
|
|
3787
3917
|
path3.join(config.memoryDir, "threads"),
|
|
3788
3918
|
config.threadingGapMinutes
|
|
3789
3919
|
);
|
|
3920
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(config);
|
|
3790
3921
|
this.tmtBuilder = new TmtBuilder(config.memoryDir, {
|
|
3791
|
-
temporalMemoryTreeEnabled:
|
|
3922
|
+
temporalMemoryTreeEnabled: lifecycleCaps.temporalMemoryTree,
|
|
3792
3923
|
tmtHourlyMinMemories: config.tmtHourlyMinMemories,
|
|
3793
3924
|
tmtSummaryMaxTokens: config.tmtSummaryMaxTokens
|
|
3794
3925
|
});
|
|
@@ -4182,6 +4313,7 @@ var Orchestrator = class _Orchestrator {
|
|
|
4182
4313
|
}
|
|
4183
4314
|
}
|
|
4184
4315
|
async deferredInitialize(signal) {
|
|
4316
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
4185
4317
|
if (this.qmd.isAvailable() && this.config.qmdMaintenanceEnabled) {
|
|
4186
4318
|
try {
|
|
4187
4319
|
log.info("QMD startup sync: updating index to match current disk state");
|
|
@@ -4215,7 +4347,7 @@ var Orchestrator = class _Orchestrator {
|
|
|
4215
4347
|
})
|
|
4216
4348
|
);
|
|
4217
4349
|
}
|
|
4218
|
-
if (this.config.
|
|
4350
|
+
if (resolveMemoryLifecycleCapabilities(this.config).embeddingFallback) {
|
|
4219
4351
|
warmupPromises.push(
|
|
4220
4352
|
this.embeddingFallback.isAvailable().then((ok) => {
|
|
4221
4353
|
log.info(
|
|
@@ -4279,9 +4411,9 @@ var Orchestrator = class _Orchestrator {
|
|
|
4279
4411
|
if (signal.aborted) return;
|
|
4280
4412
|
await this.maintenanceScheduler.autoRegisterCrons(signal);
|
|
4281
4413
|
if (signal.aborted) return;
|
|
4282
|
-
if (
|
|
4414
|
+
if (lifecycleCaps.lifecyclePolicy && this.config.qmdTierMigrationEnabled) {
|
|
4283
4415
|
try {
|
|
4284
|
-
const { runFirstStartMigration } = await import("./first-start-migration-
|
|
4416
|
+
const { runFirstStartMigration } = await import("./first-start-migration-22LPFHD5.js");
|
|
4285
4417
|
const result = await runFirstStartMigration({
|
|
4286
4418
|
storage: this.storage,
|
|
4287
4419
|
config: this.config,
|
|
@@ -4506,6 +4638,7 @@ var Orchestrator = class _Orchestrator {
|
|
|
4506
4638
|
* default storage.
|
|
4507
4639
|
*/
|
|
4508
4640
|
async runLifecyclePolicyFanout() {
|
|
4641
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
4509
4642
|
return this.runNamespaceMaintenanceFanoutForJob(
|
|
4510
4643
|
"lifecycle",
|
|
4511
4644
|
async (ctx) => {
|
|
@@ -4514,7 +4647,7 @@ var Orchestrator = class _Orchestrator {
|
|
|
4514
4647
|
const assessed = await this.runLifecyclePolicyPass(corpus, storage);
|
|
4515
4648
|
return { itemCount: assessed };
|
|
4516
4649
|
},
|
|
4517
|
-
{ enabled:
|
|
4650
|
+
{ enabled: lifecycleCaps.lifecyclePolicy }
|
|
4518
4651
|
);
|
|
4519
4652
|
}
|
|
4520
4653
|
/**
|
|
@@ -4924,15 +5057,7 @@ ${doc.content}` : doc.content,
|
|
|
4924
5057
|
return result;
|
|
4925
5058
|
}
|
|
4926
5059
|
async waitForExtractionIdle(timeoutMs = 6e4) {
|
|
4927
|
-
|
|
4928
|
-
while (this.queueProcessing || this.extractionQueue.length > 0) {
|
|
4929
|
-
if (Date.now() - started > timeoutMs) {
|
|
4930
|
-
log.warn(`waitForExtractionIdle timed out after ${timeoutMs}ms`);
|
|
4931
|
-
return false;
|
|
4932
|
-
}
|
|
4933
|
-
await new Promise((resolve) => setTimeout(resolve, 50));
|
|
4934
|
-
}
|
|
4935
|
-
return true;
|
|
5060
|
+
return this.extractionQueueCoordinator.waitForIdle(timeoutMs);
|
|
4936
5061
|
}
|
|
4937
5062
|
async waitForConsolidationIdle(timeoutMs = 6e4) {
|
|
4938
5063
|
const started = Date.now();
|
|
@@ -6832,7 +6957,7 @@ ${r.snippet.trim()}
|
|
|
6832
6957
|
recallAssemblyClockMs() {
|
|
6833
6958
|
return Date.now();
|
|
6834
6959
|
}
|
|
6835
|
-
async recallInternal(prompt, sessionKey, options = {}, caps = resolveCapabilities(this.config), graphCaps = resolveGraphConstructionCapabilities(this.config)) {
|
|
6960
|
+
async recallInternal(prompt, sessionKey, options = {}, caps = resolveCapabilities(this.config), graphCaps = resolveGraphConstructionCapabilities(this.config), lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config)) {
|
|
6836
6961
|
const recallStart = Date.now();
|
|
6837
6962
|
const backendDegradations = [];
|
|
6838
6963
|
let asOfMs;
|
|
@@ -9409,8 +9534,8 @@ ${boxLines.join("\n")}`
|
|
|
9409
9534
|
}
|
|
9410
9535
|
if (this.isRecallSectionEnabled(
|
|
9411
9536
|
"temporal-memory-tree",
|
|
9412
|
-
|
|
9413
|
-
) &&
|
|
9537
|
+
lifecycleCaps.temporalMemoryTree
|
|
9538
|
+
) && lifecycleCaps.temporalMemoryTree && recallMode !== "minimal" && recallMode !== "no_recall") {
|
|
9414
9539
|
const tmtNode = await this.tmtBuilder.getMostRelevantNode();
|
|
9415
9540
|
if (tmtNode) {
|
|
9416
9541
|
const levelLabel = tmtNode.level.charAt(0).toUpperCase() + tmtNode.level.slice(1);
|
|
@@ -10073,7 +10198,7 @@ ${tmtNode.summary}`
|
|
|
10073
10198
|
);
|
|
10074
10199
|
if (memories.length > 0) {
|
|
10075
10200
|
const supersessionOptions = {
|
|
10076
|
-
enabled:
|
|
10201
|
+
enabled: lifecycleCaps.temporalSupersession,
|
|
10077
10202
|
includeInRecall: this.config.temporalSupersessionIncludeInRecall
|
|
10078
10203
|
};
|
|
10079
10204
|
const asOfActive = typeof asOfMs === "number" && Number.isFinite(asOfMs);
|
|
@@ -11157,7 +11282,7 @@ _Context: ${topQuestion.context}_`
|
|
|
11157
11282
|
settleTask(new Error("replay extraction deadline exceeded (queue_wait)"));
|
|
11158
11283
|
}, remainingMs);
|
|
11159
11284
|
}
|
|
11160
|
-
this.
|
|
11285
|
+
this.extractionQueueCoordinator.enqueue(async () => {
|
|
11161
11286
|
if (settled) return;
|
|
11162
11287
|
if (typeof extractionDeadlineMs === "number" && extractionDeadlineMs <= Date.now()) {
|
|
11163
11288
|
settleTask(new Error("replay extraction deadline exceeded (queue_wait)"));
|
|
@@ -11183,13 +11308,6 @@ _Context: ${topQuestion.context}_`
|
|
|
11183
11308
|
}
|
|
11184
11309
|
}
|
|
11185
11310
|
});
|
|
11186
|
-
if (!this.queueProcessing) {
|
|
11187
|
-
this.queueProcessing = true;
|
|
11188
|
-
this.processQueue().catch((err) => {
|
|
11189
|
-
this.logExtractionQueueFailure(err, "processor");
|
|
11190
|
-
this.queueProcessing = false;
|
|
11191
|
-
});
|
|
11192
|
-
}
|
|
11193
11311
|
log.debug(`queued extraction from ${reason}`);
|
|
11194
11312
|
}
|
|
11195
11313
|
normalizeExtractionFingerprintTurns(turns) {
|
|
@@ -11208,7 +11326,8 @@ _Context: ${topQuestion.context}_`
|
|
|
11208
11326
|
${normalized}`).digest("hex");
|
|
11209
11327
|
}
|
|
11210
11328
|
shouldQueueExtraction(turns, options = {}) {
|
|
11211
|
-
|
|
11329
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
11330
|
+
if (!lifecycleCaps.extractionDedupe) return true;
|
|
11212
11331
|
if (!Array.isArray(turns) || turns.length === 0) return false;
|
|
11213
11332
|
const bufferKey = options.bufferKey ?? turns[0]?.sessionKey ?? "default";
|
|
11214
11333
|
const fingerprint = this.buildExtractionFingerprint(turns, bufferKey);
|
|
@@ -11232,50 +11351,6 @@ ${normalized}`).digest("hex");
|
|
|
11232
11351
|
}
|
|
11233
11352
|
return true;
|
|
11234
11353
|
}
|
|
11235
|
-
/**
|
|
11236
|
-
* Background serial queue processor.
|
|
11237
|
-
* Processes extractions one at a time to avoid race conditions.
|
|
11238
|
-
* Called automatically when items are queued.
|
|
11239
|
-
*/
|
|
11240
|
-
async processQueue() {
|
|
11241
|
-
while (this.extractionQueue.length > 0) {
|
|
11242
|
-
const task = this.extractionQueue.shift();
|
|
11243
|
-
if (task) {
|
|
11244
|
-
try {
|
|
11245
|
-
await task();
|
|
11246
|
-
} catch (err) {
|
|
11247
|
-
this.logExtractionQueueFailure(err, "task");
|
|
11248
|
-
}
|
|
11249
|
-
}
|
|
11250
|
-
}
|
|
11251
|
-
this.queueProcessing = false;
|
|
11252
|
-
}
|
|
11253
|
-
/**
|
|
11254
|
-
* Classify + log a failure from either the per-task catch inside
|
|
11255
|
-
* `processQueue()` or the outer `processQueue().catch(...)` in
|
|
11256
|
-
* `queueBufferedExtraction()`. Issue #549: `throwIfRecallAborted`
|
|
11257
|
-
* (used throughout `runExtraction`) raises an Error whose `name` is
|
|
11258
|
-
* `"AbortError"`. That path fires when `before_reset` aborts a
|
|
11259
|
-
* queued task to avoid duplicate extraction — it is intentional
|
|
11260
|
-
* cancellation, not a failure. Downgrading the log to debug
|
|
11261
|
-
* prevents spurious `error`-level lines that routinely appear
|
|
11262
|
-
* right next to a successful `persisted: N facts, M entities` log
|
|
11263
|
-
* and that confuse operators into thinking extraction is broken.
|
|
11264
|
-
* Genuine extraction failures (network, parse, I/O) still log at
|
|
11265
|
-
* `error`.
|
|
11266
|
-
*
|
|
11267
|
-
* Source differentiates the two call sites so the log message
|
|
11268
|
-
* names the right layer (`task` vs `processor`).
|
|
11269
|
-
*/
|
|
11270
|
-
logExtractionQueueFailure(err, source) {
|
|
11271
|
-
const aborted = source === "task" ? "background extraction task aborted (session transition)" : "background extraction queue processor aborted (session transition)";
|
|
11272
|
-
const failed = source === "task" ? "background extraction task failed" : "background extraction queue processor failed";
|
|
11273
|
-
if (isAbortError(err)) {
|
|
11274
|
-
log.debug(aborted);
|
|
11275
|
-
} else {
|
|
11276
|
-
log.error(failed, err);
|
|
11277
|
-
}
|
|
11278
|
-
}
|
|
11279
11354
|
/**
|
|
11280
11355
|
* Passive correction capture (issue #1581) — detects corrections expressed
|
|
11281
11356
|
* passively in conversation turns and routes them to the Correction Contract
|
|
@@ -11809,7 +11884,7 @@ ${normalized}`).digest("hex");
|
|
|
11809
11884
|
requestQmdMaintenanceForTool(reason) {
|
|
11810
11885
|
this.maintenanceScheduler.requestQmdMaintenanceForTool(reason);
|
|
11811
11886
|
}
|
|
11812
|
-
async persistExtraction(result, storage, threadIdForExtraction, sourceContext, baseNamespace, scopeProfileWritePlan, sourceText, graphCaps = resolveGraphConstructionCapabilities(this.config)) {
|
|
11887
|
+
async persistExtraction(result, storage, threadIdForExtraction, sourceContext, baseNamespace, scopeProfileWritePlan, sourceText, graphCaps = resolveGraphConstructionCapabilities(this.config), lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config)) {
|
|
11813
11888
|
const citationEnabled = this.config.inlineSourceAttributionEnabled === true;
|
|
11814
11889
|
const citationTemplate = this.config.inlineSourceAttributionFormat;
|
|
11815
11890
|
const citationContextBase = citationEnabled ? {
|
|
@@ -11984,7 +12059,7 @@ ${normalized}`).digest("hex");
|
|
|
11984
12059
|
...options.provenance ? { provenance: options.provenance } : {}
|
|
11985
12060
|
}
|
|
11986
12061
|
);
|
|
11987
|
-
if (
|
|
12062
|
+
if (lifecycleCaps.temporalSupersession && options.category === "fact" && options.entityRef && options.structuredAttributes && Object.keys(options.structuredAttributes).length > 0) {
|
|
11988
12063
|
try {
|
|
11989
12064
|
await applyTemporalSupersession({
|
|
11990
12065
|
storage: targetStorage,
|
|
@@ -12052,7 +12127,7 @@ ${normalized}`).digest("hex");
|
|
|
12052
12127
|
options.entityRef
|
|
12053
12128
|
);
|
|
12054
12129
|
}
|
|
12055
|
-
if (
|
|
12130
|
+
if (lifecycleCaps.temporalSupersession && options.entityRef && options.structuredAttributes && Object.keys(options.structuredAttributes).length > 0) {
|
|
12056
12131
|
let hashDedupMatchingFact;
|
|
12057
12132
|
let hashDedupLookupComplete = false;
|
|
12058
12133
|
try {
|
|
@@ -12131,7 +12206,7 @@ ${normalized}`).digest("hex");
|
|
|
12131
12206
|
...options.provenance ? { provenance: options.provenance } : {}
|
|
12132
12207
|
}
|
|
12133
12208
|
);
|
|
12134
|
-
if (
|
|
12209
|
+
if (lifecycleCaps.temporalSupersession && options.entityRef && options.structuredAttributes && Object.keys(options.structuredAttributes).length > 0) {
|
|
12135
12210
|
try {
|
|
12136
12211
|
await applyTemporalSupersession({
|
|
12137
12212
|
storage: sharedStorage,
|
|
@@ -12309,7 +12384,7 @@ ${normalized}`).digest("hex");
|
|
|
12309
12384
|
let judgeVerdictsByFactIndex = null;
|
|
12310
12385
|
let judgeGatedCount = 0;
|
|
12311
12386
|
this.lastPersistExtractionDeferredCount = 0;
|
|
12312
|
-
if (
|
|
12387
|
+
if (lifecycleCaps.extractionJudge) {
|
|
12313
12388
|
let preJudgeRedactionRules = [];
|
|
12314
12389
|
try {
|
|
12315
12390
|
preJudgeRedactionRules = await redactionRulesFor(storage.dir);
|
|
@@ -12353,7 +12428,7 @@ ${normalized}`).digest("hex");
|
|
|
12353
12428
|
candidateToFactIndex.push(fi);
|
|
12354
12429
|
}
|
|
12355
12430
|
const judgeTelemetryOpts = {
|
|
12356
|
-
enabled:
|
|
12431
|
+
enabled: lifecycleCaps.extractionJudgeTelemetry,
|
|
12357
12432
|
memoryDir: this.config.memoryDir
|
|
12358
12433
|
};
|
|
12359
12434
|
const judgeTrainingOpts = {
|
|
@@ -12478,7 +12553,7 @@ ${normalized}`).digest("hex");
|
|
|
12478
12553
|
);
|
|
12479
12554
|
}
|
|
12480
12555
|
}
|
|
12481
|
-
if (
|
|
12556
|
+
if (lifecycleCaps.extractionScopeClassification && this.config.namespacesEnabled && fact.scope === "global" && !routedNamespaceExplicit) {
|
|
12482
12557
|
const currentNs = this.storageDirNamespace(targetStorage.dir);
|
|
12483
12558
|
if (currentNs !== this.config.sharedNamespace && profileAllowsSharedWrites) {
|
|
12484
12559
|
try {
|
|
@@ -12840,7 +12915,7 @@ ${normalized}`).digest("hex");
|
|
|
12840
12915
|
// #1578 r3: an extracted end-only bound (validFrom absent) is
|
|
12841
12916
|
// historical, not a new authoritative state — never let it
|
|
12842
12917
|
// supersede a later active fact (codex P1 on :15534).
|
|
12843
|
-
enabled:
|
|
12918
|
+
enabled: lifecycleCaps.temporalSupersession && !(biTemporal && !biTemporal.validFrom)
|
|
12844
12919
|
});
|
|
12845
12920
|
} catch (err) {
|
|
12846
12921
|
log.warn(`temporal-supersession (chunked): unexpected error: ${err}`);
|
|
@@ -13003,7 +13078,7 @@ ${normalized}`).digest("hex");
|
|
|
13003
13078
|
entityRef: supersessionEntityRef,
|
|
13004
13079
|
structuredAttributes: fact.structuredAttributes,
|
|
13005
13080
|
createdAt: supersessionOrderingAt(biTemporal?.validFrom ?? sourceContext?.validAt),
|
|
13006
|
-
enabled:
|
|
13081
|
+
enabled: lifecycleCaps.temporalSupersession && !(biTemporal && !biTemporal.validFrom)
|
|
13007
13082
|
});
|
|
13008
13083
|
} catch (err) {
|
|
13009
13084
|
log.warn(`temporal-supersession: unexpected error: ${err}`);
|
|
@@ -13257,7 +13332,7 @@ ${normalized}`).digest("hex");
|
|
|
13257
13332
|
}
|
|
13258
13333
|
}
|
|
13259
13334
|
async indexPersistedMemory(storage, memoryId) {
|
|
13260
|
-
if (!this.config.
|
|
13335
|
+
if (!resolveMemoryLifecycleCapabilities(this.config).embeddingFallback) return;
|
|
13261
13336
|
if (!await this.embeddingFallback.isAvailable()) return;
|
|
13262
13337
|
const memory = await storage.getMemoryById(memoryId);
|
|
13263
13338
|
if (!memory) return;
|
|
@@ -13385,6 +13460,7 @@ ${normalized}`).digest("hex");
|
|
|
13385
13460
|
/** IDs of facts persisted in the last extraction */
|
|
13386
13461
|
lastPersistedIds = [];
|
|
13387
13462
|
async runConsolidation() {
|
|
13463
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
13388
13464
|
log.info("running consolidation pass");
|
|
13389
13465
|
let merged = 0;
|
|
13390
13466
|
let invalidated = 0;
|
|
@@ -13549,7 +13625,7 @@ ${normalized}`).digest("hex");
|
|
|
13549
13625
|
}
|
|
13550
13626
|
}
|
|
13551
13627
|
}
|
|
13552
|
-
if (
|
|
13628
|
+
if (lifecycleCaps.lifecyclePolicy) {
|
|
13553
13629
|
try {
|
|
13554
13630
|
const lightSleepStartedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
13555
13631
|
const lifecycleCorpus = await this.storage.readAllMemories();
|
|
@@ -13699,7 +13775,7 @@ ${normalized}`).digest("hex");
|
|
|
13699
13775
|
const meta = await this.storage.loadMeta();
|
|
13700
13776
|
meta.lastConsolidationAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
13701
13777
|
await this.storage.saveMeta(meta);
|
|
13702
|
-
if (
|
|
13778
|
+
if (lifecycleCaps.temporalMemoryTree) {
|
|
13703
13779
|
try {
|
|
13704
13780
|
const tmtEntries = allMemories.filter(
|
|
13705
13781
|
(m) => m.frontmatter.status !== "superseded" && m.frontmatter.status !== "archived" && m.frontmatter.status !== "forgotten" && m.frontmatter.status !== "pending_review"
|
|
@@ -14095,6 +14171,7 @@ ${texts.map((t, i) => `[${i + 1}] ${t}`).join("\n\n")}`;
|
|
|
14095
14171
|
let updatedCount = 0;
|
|
14096
14172
|
let disputedCount = 0;
|
|
14097
14173
|
let evaluatedCount = 0;
|
|
14174
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
14098
14175
|
const thresholds = this.effectiveLifecycleThresholds();
|
|
14099
14176
|
const policy = {
|
|
14100
14177
|
promoteHeatThreshold: thresholds.promoteHeatThreshold,
|
|
@@ -14134,7 +14211,7 @@ ${texts.map((t, i) => `[${i + 1}] ${t}`).join("\n\n")}`;
|
|
|
14134
14211
|
});
|
|
14135
14212
|
if (wrote) updatedCount += 1;
|
|
14136
14213
|
}
|
|
14137
|
-
if (!
|
|
14214
|
+
if (!lifecycleCaps.lifecycleMetrics) return updatedCount;
|
|
14138
14215
|
const total = evaluatedCount;
|
|
14139
14216
|
const metrics = {
|
|
14140
14217
|
generatedAt: nowIso,
|
|
@@ -15137,7 +15214,7 @@ ${lines.join("\n\n")}`;
|
|
|
15137
15214
|
* `memoryDir` root, an exclusion list for `namespaces/*`).
|
|
15138
15215
|
*/
|
|
15139
15216
|
async semanticDedupLookup(content, limit, targetStorage) {
|
|
15140
|
-
if (!this.config.
|
|
15217
|
+
if (!resolveMemoryLifecycleCapabilities(this.config).embeddingFallback) {
|
|
15141
15218
|
throw new Error("semantic dedup: embedding backend not configured");
|
|
15142
15219
|
}
|
|
15143
15220
|
if (!await this.embeddingFallback.isAvailable()) {
|
|
@@ -15187,7 +15264,7 @@ ${lines.join("\n\n")}`;
|
|
|
15187
15264
|
return { pathPrefix: rel };
|
|
15188
15265
|
}
|
|
15189
15266
|
async searchEmbeddingFallback(query, limit) {
|
|
15190
|
-
if (!this.config.
|
|
15267
|
+
if (!resolveMemoryLifecycleCapabilities(this.config).embeddingFallback) return [];
|
|
15191
15268
|
if (!await this.embeddingFallback.isAvailable()) return [];
|
|
15192
15269
|
const hits = await this.embeddingFallback.search(query, limit);
|
|
15193
15270
|
if (hits.length === 0) return [];
|
|
@@ -15710,6 +15787,7 @@ ${lines.join("\n\n")}`;
|
|
|
15710
15787
|
return { memoryByPath, checkedPaths, unreadablePaths, completed: true };
|
|
15711
15788
|
}
|
|
15712
15789
|
filterSearchResultsByRecallSafety(results, memoryByPath, options) {
|
|
15790
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
15713
15791
|
let lifecycleFilteredCount = 0;
|
|
15714
15792
|
let temporalSupersededFilteredCount = 0;
|
|
15715
15793
|
let biTemporalExpiredFilteredCount = 0;
|
|
@@ -15730,8 +15808,8 @@ ${lines.join("\n\n")}`;
|
|
|
15730
15808
|
continue;
|
|
15731
15809
|
}
|
|
15732
15810
|
if (options?.allowLifecycleFiltered !== true && shouldFilterLifecycleRecallCandidate(memory.frontmatter, {
|
|
15733
|
-
lifecyclePolicyEnabled:
|
|
15734
|
-
lifecycleFilterStaleEnabled:
|
|
15811
|
+
lifecyclePolicyEnabled: lifecycleCaps.lifecyclePolicy,
|
|
15812
|
+
lifecycleFilterStaleEnabled: lifecycleCaps.lifecycleFilterStale
|
|
15735
15813
|
})) {
|
|
15736
15814
|
lifecycleFilteredCount += 1;
|
|
15737
15815
|
continue;
|
|
@@ -15754,7 +15832,7 @@ ${lines.join("\n\n")}`;
|
|
|
15754
15832
|
// half-open `[valid_at, invalid_at)` evaluation in isValidAsOf
|
|
15755
15833
|
// is the authoritative gate for historical recall.
|
|
15756
15834
|
shouldFilterSupersededFromRecall(memory.frontmatter, {
|
|
15757
|
-
enabled:
|
|
15835
|
+
enabled: lifecycleCaps.temporalSupersession,
|
|
15758
15836
|
includeInRecall: this.config.temporalSupersessionIncludeInRecall
|
|
15759
15837
|
})
|
|
15760
15838
|
) {
|
|
@@ -15844,6 +15922,7 @@ ${lines.join("\n\n")}`;
|
|
|
15844
15922
|
* Returns re-ranked results.
|
|
15845
15923
|
*/
|
|
15846
15924
|
async boostSearchResults(results, _recallNamespaces, prompt, preloadedMemoryMap, options) {
|
|
15925
|
+
const lifecycleCaps = resolveMemoryLifecycleCapabilities(this.config);
|
|
15847
15926
|
if (results.length === 0) return results;
|
|
15848
15927
|
const safety = await this.filterSearchResultsForRecall(
|
|
15849
15928
|
results,
|
|
@@ -15977,7 +16056,7 @@ ${lines.join("\n\n")}`;
|
|
|
15977
16056
|
const lifecycleDelta = lifecycleRecallScoreAdjustment(
|
|
15978
16057
|
memory.frontmatter,
|
|
15979
16058
|
{
|
|
15980
|
-
lifecyclePolicyEnabled:
|
|
16059
|
+
lifecyclePolicyEnabled: lifecycleCaps.lifecyclePolicy
|
|
15981
16060
|
}
|
|
15982
16061
|
);
|
|
15983
16062
|
score += applyUtilityRankingRuntimeDelta(
|
|
@@ -16313,4 +16392,4 @@ export {
|
|
|
16313
16392
|
resolvePersistedMemoryRelativePath,
|
|
16314
16393
|
Orchestrator
|
|
16315
16394
|
};
|
|
16316
|
-
//# sourceMappingURL=chunk-
|
|
16395
|
+
//# sourceMappingURL=chunk-HEDZUSCS.js.map
|