@graphorin/memory 0.6.0 → 0.7.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/CHANGELOG.md +83 -0
- package/README.md +24 -7
- package/dist/conflict/index.js +0 -1
- package/dist/conflict/pipeline.js +0 -1
- package/dist/conflict/pipeline.js.map +1 -1
- package/dist/conflict/stages/stage3-heuristic-regex.js +0 -1
- package/dist/conflict/stages/stage3-heuristic-regex.js.map +1 -1
- package/dist/conflict/types.d.ts +1 -1
- package/dist/conflict/types.js.map +1 -1
- package/dist/consolidator/index.js +2 -0
- package/dist/consolidator/index.js.map +1 -1
- package/dist/consolidator/lock.js +7 -1
- package/dist/consolidator/lock.js.map +1 -1
- package/dist/consolidator/phases/deep.js +19 -12
- package/dist/consolidator/phases/deep.js.map +1 -1
- package/dist/consolidator/phases/induce.d.ts.map +1 -1
- package/dist/consolidator/phases/induce.js +2 -3
- package/dist/consolidator/phases/induce.js.map +1 -1
- package/dist/consolidator/phases/reflect.js +35 -8
- package/dist/consolidator/phases/reflect.js.map +1 -1
- package/dist/consolidator/phases/standard.js +199 -28
- package/dist/consolidator/phases/standard.js.map +1 -1
- package/dist/consolidator/reconcile.js +16 -15
- package/dist/consolidator/reconcile.js.map +1 -1
- package/dist/consolidator/runtime.d.ts.map +1 -1
- package/dist/consolidator/runtime.js +129 -47
- package/dist/consolidator/runtime.js.map +1 -1
- package/dist/consolidator/scheduler.d.ts +17 -3
- package/dist/consolidator/scheduler.d.ts.map +1 -1
- package/dist/consolidator/scheduler.js.map +1 -1
- package/dist/consolidator/types.d.ts +30 -1
- package/dist/consolidator/types.d.ts.map +1 -1
- package/dist/consolidator/types.js +10 -0
- package/dist/consolidator/types.js.map +1 -1
- package/dist/context-engine/compaction/clear-tool-results.d.ts +1 -1
- package/dist/context-engine/compaction/clear-tool-results.js +1 -1
- package/dist/context-engine/compaction/clear-tool-results.js.map +1 -1
- package/dist/context-engine/compaction/compactor.d.ts +1 -0
- package/dist/context-engine/compaction/compactor.d.ts.map +1 -1
- package/dist/context-engine/compaction/compactor.js +32 -8
- package/dist/context-engine/compaction/compactor.js.map +1 -1
- package/dist/context-engine/compaction/hooks/types.d.ts +1 -1
- package/dist/context-engine/compaction/index.d.ts +1 -0
- package/dist/context-engine/compaction/templates/marker.d.ts +33 -0
- package/dist/context-engine/compaction/templates/marker.d.ts.map +1 -0
- package/dist/context-engine/compaction/templates/marker.js +34 -0
- package/dist/context-engine/compaction/templates/marker.js.map +1 -0
- package/dist/context-engine/compaction/templates/summary-9-section.d.ts +1 -1
- package/dist/context-engine/compaction/templates/summary-9-section.d.ts.map +1 -1
- package/dist/context-engine/compaction/templates/summary-9-section.js +4 -3
- package/dist/context-engine/compaction/templates/summary-9-section.js.map +1 -1
- package/dist/context-engine/engine.d.ts +7 -176
- package/dist/context-engine/engine.d.ts.map +1 -1
- package/dist/context-engine/engine.js +0 -2
- package/dist/context-engine/engine.js.map +1 -1
- package/dist/context-engine/index.d.ts +8 -49
- package/dist/context-engine/io-types.d.ts +144 -0
- package/dist/context-engine/io-types.d.ts.map +1 -0
- package/dist/context-engine/locale-packs/types.d.ts +1 -1
- package/dist/context-engine/locale-packs/types.js.map +1 -1
- package/dist/context-engine/privacy-filter.d.ts +1 -2
- package/dist/context-engine/privacy-filter.d.ts.map +1 -1
- package/dist/context-engine/privacy-filter.js +1 -2
- package/dist/context-engine/privacy-filter.js.map +1 -1
- package/dist/errors/index.d.ts +2 -2
- package/dist/errors/index.js +2 -2
- package/dist/errors/index.js.map +1 -1
- package/dist/facade.d.ts +43 -52
- package/dist/facade.d.ts.map +1 -1
- package/dist/facade.js +5 -3
- package/dist/facade.js.map +1 -1
- package/dist/graph/entity-resolver.js +1 -1
- package/dist/graph/entity-resolver.js.map +1 -1
- package/dist/index.d.ts +17 -15
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +5 -7
- package/dist/index.js.map +1 -1
- package/dist/internal/envelope.js +57 -0
- package/dist/internal/envelope.js.map +1 -0
- package/dist/internal/injection-heuristics.js +0 -0
- package/dist/internal/injection-heuristics.js.map +1 -1
- package/dist/internal/llm-json.js +40 -0
- package/dist/internal/llm-json.js.map +1 -0
- package/dist/internal/storage-adapter.d.ts +23 -10
- package/dist/internal/storage-adapter.d.ts.map +1 -1
- package/dist/memory-interface.d.ts +131 -0
- package/dist/memory-interface.d.ts.map +1 -0
- package/dist/package.js +6 -0
- package/dist/package.js.map +1 -0
- package/dist/search/iterative.d.ts.map +1 -1
- package/dist/search/iterative.js +2 -3
- package/dist/search/iterative.js.map +1 -1
- package/dist/search/query-transform.d.ts.map +1 -1
- package/dist/search/query-transform.js +2 -3
- package/dist/search/query-transform.js.map +1 -1
- package/dist/tiers/episodic-memory.js +3 -3
- package/dist/tiers/episodic-memory.js.map +1 -1
- package/dist/tiers/index.d.ts +2 -2
- package/dist/tiers/insight-memory.js +1 -1
- package/dist/tiers/insight-memory.js.map +1 -1
- package/dist/tiers/procedural-memory.d.ts +1 -1
- package/dist/tiers/procedural-memory.js +2 -2
- package/dist/tiers/procedural-memory.js.map +1 -1
- package/dist/tiers/semantic-memory.d.ts +58 -4
- package/dist/tiers/semantic-memory.d.ts.map +1 -1
- package/dist/tiers/semantic-memory.js +103 -20
- package/dist/tiers/semantic-memory.js.map +1 -1
- package/dist/tools/block-tools.d.ts +19 -57
- package/dist/tools/block-tools.d.ts.map +1 -1
- package/dist/tools/block-tools.js.map +1 -1
- package/dist/tools/fact-tools.d.ts +53 -214
- package/dist/tools/fact-tools.d.ts.map +1 -1
- package/dist/tools/fact-tools.js +3 -2
- package/dist/tools/fact-tools.js.map +1 -1
- package/dist/tools/recall-tools.d.ts +34 -175
- package/dist/tools/recall-tools.d.ts.map +1 -1
- package/dist/tools/recall-tools.js +5 -4
- package/dist/tools/recall-tools.js.map +1 -1
- package/dist/tools/runbook-tools.d.ts +15 -58
- package/dist/tools/runbook-tools.d.ts.map +1 -1
- package/dist/tools/runbook-tools.js.map +1 -1
- package/dist/tools/types.d.ts +1 -1
- package/package.json +18 -17
- package/src/conflict/index.ts +29 -0
- package/src/conflict/locale-packs/en.ts +142 -0
- package/src/conflict/locale-packs/index.ts +17 -0
- package/src/conflict/locale-packs/types.ts +138 -0
- package/src/conflict/pipeline.ts +371 -0
- package/src/conflict/stages/helpers.ts +65 -0
- package/src/conflict/stages/stage1-exact-dedup.ts +40 -0
- package/src/conflict/stages/stage2-embedding-three-zone.ts +54 -0
- package/src/conflict/stages/stage3-heuristic-regex.ts +51 -0
- package/src/conflict/stages/stage4-subject-predicate.ts +46 -0
- package/src/conflict/stages/stage5-defer-to-deep.ts +34 -0
- package/src/conflict/types.ts +263 -0
- package/src/consolidator/budget.ts +312 -0
- package/src/consolidator/decay.ts +246 -0
- package/src/consolidator/dlq.ts +61 -0
- package/src/consolidator/errors.ts +87 -0
- package/src/consolidator/idempotency.ts +27 -0
- package/src/consolidator/index.ts +269 -0
- package/src/consolidator/lock.ts +141 -0
- package/src/consolidator/noise-filter.ts +235 -0
- package/src/consolidator/phases/deep.ts +308 -0
- package/src/consolidator/phases/induce.ts +423 -0
- package/src/consolidator/phases/learned-context.ts +233 -0
- package/src/consolidator/phases/light.ts +166 -0
- package/src/consolidator/phases/reflect.ts +504 -0
- package/src/consolidator/phases/standard.ts +1002 -0
- package/src/consolidator/reconcile.ts +273 -0
- package/src/consolidator/runtime.ts +1049 -0
- package/src/consolidator/scheduler.ts +182 -0
- package/src/consolidator/triggers.ts +134 -0
- package/src/consolidator/types.ts +622 -0
- package/src/context-engine/annotations.ts +161 -0
- package/src/context-engine/auto-recall.ts +92 -0
- package/src/context-engine/compaction/clear-tool-results.ts +232 -0
- package/src/context-engine/compaction/compactor.ts +403 -0
- package/src/context-engine/compaction/hooks/reanchor-persona-block.ts +55 -0
- package/src/context-engine/compaction/hooks/reanchor-pinned-facts.ts +66 -0
- package/src/context-engine/compaction/hooks/reanchor-project-rules.ts +57 -0
- package/src/context-engine/compaction/hooks/reanchor-recent-results.ts +116 -0
- package/src/context-engine/compaction/hooks/types.ts +68 -0
- package/src/context-engine/compaction/index.ts +60 -0
- package/src/context-engine/compaction/templates/marker.ts +33 -0
- package/src/context-engine/compaction/templates/summary-9-section.ts +223 -0
- package/src/context-engine/compaction/thresholds.ts +107 -0
- package/src/context-engine/compaction/types.ts +255 -0
- package/src/context-engine/engine.ts +970 -0
- package/src/context-engine/index.ts +118 -0
- package/src/context-engine/io-types.ts +162 -0
- package/src/context-engine/locale-packs/en.ts +107 -0
- package/src/context-engine/locale-packs/index.ts +19 -0
- package/src/context-engine/locale-packs/resolver.ts +197 -0
- package/src/context-engine/locale-packs/types.ts +177 -0
- package/src/context-engine/metadata.ts +114 -0
- package/src/context-engine/preambles/inbound-en.ts +19 -0
- package/src/context-engine/privacy-filter.ts +190 -0
- package/src/context-engine/templates/base-en.ts +19 -0
- package/src/context-engine/templates/composer.ts +91 -0
- package/src/context-engine/token-budget.ts +319 -0
- package/src/context-engine/token-counter.ts +157 -0
- package/src/errors/index.ts +273 -0
- package/src/facade.ts +750 -0
- package/src/graph/entity-resolver.ts +364 -0
- package/src/graph/index.ts +24 -0
- package/src/index.ts +259 -0
- package/src/internal/contextualize.ts +173 -0
- package/src/internal/embedder-binding.ts +53 -0
- package/src/internal/envelope.ts +70 -0
- package/src/internal/id.ts +23 -0
- package/src/internal/injection-heuristics.ts +0 -0
- package/src/internal/llm-json.ts +38 -0
- package/src/internal/spans.ts +35 -0
- package/src/internal/storage-adapter.ts +963 -0
- package/src/memory-interface.ts +158 -0
- package/src/migration/embedder-migration.ts +237 -0
- package/src/migration/index.ts +13 -0
- package/src/search/explain.ts +123 -0
- package/src/search/fit-weights.ts +109 -0
- package/src/search/graph-ppr.ts +38 -0
- package/src/search/index.ts +55 -0
- package/src/search/iterative.ts +658 -0
- package/src/search/query-transform.ts +285 -0
- package/src/search/rrf.ts +225 -0
- package/src/search/trust.ts +55 -0
- package/src/search/types.ts +50 -0
- package/src/tiers/episodic-memory.ts +463 -0
- package/src/tiers/index.ts +50 -0
- package/src/tiers/insight-memory.ts +208 -0
- package/src/tiers/procedural-memory.ts +482 -0
- package/src/tiers/semantic-memory.ts +1729 -0
- package/src/tiers/session-memory.ts +271 -0
- package/src/tiers/shared-memory.ts +62 -0
- package/src/tiers/working-memory.ts +368 -0
- package/src/tools/block-tools.ts +172 -0
- package/src/tools/fact-tools.ts +473 -0
- package/src/tools/index.ts +109 -0
- package/src/tools/recall-tools.ts +303 -0
- package/src/tools/runbook-tools.ts +107 -0
- package/src/tools/taint.ts +39 -0
- package/src/tools/types.ts +37 -0
- package/dist/conflict/locale-packs/index.js +0 -4
- package/dist/context-engine/compaction/index.js +0 -10
- package/dist/context-engine/index.d.ts.map +0 -1
- package/dist/context-engine/index.js +0 -25
- package/dist/context-engine/locale-packs/index.js +0 -4
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import { withMemorySpan } from "../internal/spans.js";
|
|
2
2
|
import { DEFAULT_SALIENCE_WEIGHTS } from "../consolidator/decay.js";
|
|
3
3
|
import { QuarantinePromotionRefusedError } from "../errors/index.js";
|
|
4
|
+
import { detectMemoryInjection } from "../internal/injection-heuristics.js";
|
|
4
5
|
import { contextualize } from "../internal/contextualize.js";
|
|
5
6
|
import { newMemoryId } from "../internal/id.js";
|
|
6
7
|
import { normalizeEntityName } from "../graph/entity-resolver.js";
|
|
7
8
|
import { DEFAULT_MAX_ITERATIONS, runIterativeRetrieval } from "../search/iterative.js";
|
|
8
9
|
import { WeightedRRFReranker, fuseRrf, fuseWeighted } from "../search/rrf.js";
|
|
9
|
-
import { detectMemoryInjection } from "../internal/injection-heuristics.js";
|
|
10
10
|
import { explainRecall } from "../search/explain.js";
|
|
11
11
|
import { pprActivation } from "../search/graph-ppr.js";
|
|
12
12
|
import { trustDiscount } from "../search/trust.js";
|
|
@@ -37,8 +37,10 @@ var SemanticMemory = class {
|
|
|
37
37
|
#entityResolver;
|
|
38
38
|
#grader;
|
|
39
39
|
#iterativeMaxIterations;
|
|
40
|
+
#iterativeDifficultyThreshold;
|
|
40
41
|
#reranker;
|
|
41
42
|
#trustWeights;
|
|
43
|
+
#searchDefaults;
|
|
42
44
|
constructor(args) {
|
|
43
45
|
this.#store = args.store;
|
|
44
46
|
this.#tracer = args.tracer;
|
|
@@ -51,7 +53,9 @@ var SemanticMemory = class {
|
|
|
51
53
|
this.#entityResolver = args.entityResolver ?? null;
|
|
52
54
|
this.#grader = args.grader ?? null;
|
|
53
55
|
this.#iterativeMaxIterations = args.iterativeMaxIterations ?? DEFAULT_MAX_ITERATIONS;
|
|
56
|
+
this.#iterativeDifficultyThreshold = args.iterativeDifficultyThreshold;
|
|
54
57
|
this.#trustWeights = args.trustWeights ?? DEFAULT_SALIENCE_WEIGHTS;
|
|
58
|
+
this.#searchDefaults = args.searchDefaults ?? {};
|
|
55
59
|
}
|
|
56
60
|
/** Replace the active reranker. Returns the previous instance. */
|
|
57
61
|
setReranker(reranker) {
|
|
@@ -230,7 +234,11 @@ var SemanticMemory = class {
|
|
|
230
234
|
} catch {}
|
|
231
235
|
}
|
|
232
236
|
/** Hybrid (vector + FTS5) search merged through the configured reranker. */
|
|
233
|
-
async search(scope, query,
|
|
237
|
+
async search(scope, query, callOpts = {}) {
|
|
238
|
+
const opts = {
|
|
239
|
+
...this.#searchDefaults,
|
|
240
|
+
...callOpts
|
|
241
|
+
};
|
|
234
242
|
return withMemorySpan(this.#tracer, "memory.search.semantic", scope, { "memory.search.query_length": query.length }, async (span) => {
|
|
235
243
|
const candidateTopK = opts.candidateTopK ?? 60;
|
|
236
244
|
const finalTopK = opts.topK ?? 10;
|
|
@@ -240,6 +248,8 @@ var SemanticMemory = class {
|
|
|
240
248
|
const wGraph = weighted?.weights.graph ?? 1;
|
|
241
249
|
const wEntity = weighted?.weights.entity ?? 1;
|
|
242
250
|
const queries = await this.#expandQueries(query, opts);
|
|
251
|
+
const variantVectors = await this.#tryBatchEmbedQueries(queries);
|
|
252
|
+
const hydeHitsPromise = this.#tryHyde(scope, query, opts, candidateTopK);
|
|
243
253
|
const lists = [];
|
|
244
254
|
const listWeights = [];
|
|
245
255
|
const listLabels = [];
|
|
@@ -260,7 +270,8 @@ var SemanticMemory = class {
|
|
|
260
270
|
lists.push(ftsHits);
|
|
261
271
|
listWeights.push(wFts);
|
|
262
272
|
listLabels.push(`fts_${queries.indexOf(q)}`);
|
|
263
|
-
const
|
|
273
|
+
const preVector = variantVectors?.get(q);
|
|
274
|
+
const vectorHits = preVector !== void 0 ? await this.#vectorSearchWithVector(scope, preVector, candidateTopK, opts.asOf, opts.includeQuarantined, opts.includeSuperseded, opts.owner) : await this.#tryVectorSearch(scope, q, candidateTopK, opts.asOf, opts.includeQuarantined, opts.includeSuperseded, opts.owner);
|
|
264
275
|
if (vectorHits.length > 0) {
|
|
265
276
|
lists.push(vectorHits);
|
|
266
277
|
listWeights.push(wVector);
|
|
@@ -272,7 +283,7 @@ var SemanticMemory = class {
|
|
|
272
283
|
isPrimary = false;
|
|
273
284
|
}
|
|
274
285
|
}
|
|
275
|
-
const hydeHits = await
|
|
286
|
+
const hydeHits = await hydeHitsPromise;
|
|
276
287
|
if (hydeHits.length > 0) {
|
|
277
288
|
lists.push(hydeHits);
|
|
278
289
|
listWeights.push(wVector);
|
|
@@ -294,7 +305,7 @@ var SemanticMemory = class {
|
|
|
294
305
|
weights: listWeights,
|
|
295
306
|
...weighted.k !== void 0 ? { k: weighted.k } : {}
|
|
296
307
|
}) : this.#reranker;
|
|
297
|
-
const fusedTopK = opts.decay !== void 0 || (opts.tags?.length ?? 0) > 0 || opts.owner !== void 0 || (opts.expandHops ?? 0) > 0 || opts.entityMatch === true ? Math.max(finalTopK, lists.reduce((n, l) => n + l.length, 0)) : finalTopK;
|
|
308
|
+
const fusedTopK = opts.decay !== void 0 || (opts.tags?.length ?? 0) > 0 || opts.owner !== void 0 || (opts.expandHops ?? 0) > 0 || opts.entityMatch === true || opts.trustWeighting !== "off" || opts.includeQuarantined === true ? Math.max(finalTopK, lists.reduce((n, l) => n + l.length, 0)) : finalTopK;
|
|
298
309
|
const fused = await reranker.rerank(query, lists, {
|
|
299
310
|
topK: fusedTopK,
|
|
300
311
|
labels: listLabels,
|
|
@@ -310,7 +321,7 @@ var SemanticMemory = class {
|
|
|
310
321
|
const ownerFiltered = wantedOwners !== null ? filtered.filter((h) => wantedOwners.includes(h.record.owner ?? "user")) : filtered;
|
|
311
322
|
const ranked = (opts.trustWeighting === "off" ? ownerFiltered : this.#applyTrustDiscount(ownerFiltered)).slice(0, finalTopK);
|
|
312
323
|
if (ranked.length > 0 && typeof this.#store.semantic.markAccessed === "function") try {
|
|
313
|
-
await this.#store.semantic.markAccessed(ranked.map((h) => h.record.id));
|
|
324
|
+
await this.#store.semantic.markAccessed(ranked.map((h) => h.record.id), void 0, scope);
|
|
314
325
|
} catch {}
|
|
315
326
|
const explanation = explainRecall(ranked, {
|
|
316
327
|
query,
|
|
@@ -364,12 +375,16 @@ var SemanticMemory = class {
|
|
|
364
375
|
idOf: (hit) => hit.record.id,
|
|
365
376
|
grader: this.#grader,
|
|
366
377
|
fuse: (lists) => fuseRrf(lists, 60)
|
|
367
|
-
}, {
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
378
|
+
}, (() => {
|
|
379
|
+
const difficultyThreshold = opts.difficultyThreshold ?? this.#iterativeDifficultyThreshold;
|
|
380
|
+
return {
|
|
381
|
+
maxIterations: opts.maxIterations ?? this.#iterativeMaxIterations,
|
|
382
|
+
maxResults: opts.topK ?? 10,
|
|
383
|
+
...opts.forceHard !== void 0 ? { forceHard: opts.forceHard } : {},
|
|
384
|
+
...opts.signal !== void 0 ? { signal: opts.signal } : {},
|
|
385
|
+
...difficultyThreshold !== void 0 ? { difficulty: { threshold: difficultyThreshold } } : {}
|
|
386
|
+
};
|
|
387
|
+
})());
|
|
373
388
|
span.setAttributes({
|
|
374
389
|
"memory.search.semantic.iterative.gate_hard": result.gateHard,
|
|
375
390
|
"memory.search.semantic.iterative.iterations": result.iterations,
|
|
@@ -465,16 +480,51 @@ var SemanticMemory = class {
|
|
|
465
480
|
}
|
|
466
481
|
}
|
|
467
482
|
span.setAttributes({ "memory.semantic.validate.forced": force });
|
|
468
|
-
await this.#store.semantic.setStatus(factId, "active", reason);
|
|
483
|
+
await this.#store.semantic.setStatus(factId, "active", reason, scope);
|
|
484
|
+
if (existing !== null && existing.supersedes !== void 0) {
|
|
485
|
+
const oldFact = await this.#fetchExisting(existing.supersedes);
|
|
486
|
+
if (oldFact !== null && oldFact.supersededBy === void 0 && oldFact.validTo === void 0) {
|
|
487
|
+
span.setAttributes({ "memory.semantic.validate.completed_supersede": true });
|
|
488
|
+
await this.#store.semantic.supersede(existing.supersedes, {
|
|
489
|
+
...existing,
|
|
490
|
+
status: "active"
|
|
491
|
+
}, reason ?? "validated-supersede");
|
|
492
|
+
}
|
|
493
|
+
}
|
|
469
494
|
});
|
|
470
495
|
}
|
|
471
|
-
/**
|
|
472
|
-
|
|
473
|
-
|
|
496
|
+
/**
|
|
497
|
+
* Mark `oldId` superseded by a new fact. Returns the new record.
|
|
498
|
+
*
|
|
499
|
+
* W-019 (security-first, knowledge-preserving): when the successor
|
|
500
|
+
* lands QUARANTINED (the default for `extraction`/synthesized
|
|
501
|
+
* provenance), the old ACTIVE fact's validity interval is NOT closed
|
|
502
|
+
* - default recall keeps returning the old knowledge until the
|
|
503
|
+
* successor passes {@link validate}, which completes the closure.
|
|
504
|
+
* The link is recorded on the successor's `supersedes` field. With
|
|
505
|
+
* `autoPromoteSynthesized` (threaded from the consolidator's
|
|
506
|
+
* `autoPromoteExtraction` escape hatch) an injection-clean successor
|
|
507
|
+
* is active immediately and the interval closes right away - the
|
|
508
|
+
* pre-W-019 behaviour. Inverting the default (auto-activating the
|
|
509
|
+
* successor) would hand a MINJA attacker instant active memory via
|
|
510
|
+
* any text the reconciler classifies as an 'update'.
|
|
511
|
+
*/
|
|
512
|
+
async supersede(scope, oldId, newInput, reason, options) {
|
|
513
|
+
return withMemorySpan(this.#tracer, "memory.write.semantic", scope, { "memory.semantic.action": "supersede" }, async (span) => {
|
|
474
514
|
const newFact = await this.remember(scope, {
|
|
475
515
|
...newInput,
|
|
476
516
|
supersedes: oldId
|
|
477
|
-
}, {
|
|
517
|
+
}, {
|
|
518
|
+
pipeline: "off",
|
|
519
|
+
...options?.autoPromoteSynthesized === true ? { autoPromoteSynthesized: true } : {}
|
|
520
|
+
});
|
|
521
|
+
if (newFact.status === "quarantined") {
|
|
522
|
+
span.setAttributes({ "memory.semantic.supersede.pending": true });
|
|
523
|
+
return {
|
|
524
|
+
old: oldId,
|
|
525
|
+
new: newFact
|
|
526
|
+
};
|
|
527
|
+
}
|
|
478
528
|
await this.#store.semantic.supersede(oldId, newFact, reason);
|
|
479
529
|
return {
|
|
480
530
|
old: oldId,
|
|
@@ -488,7 +538,7 @@ var SemanticMemory = class {
|
|
|
488
538
|
"memory.semantic.action": "forget",
|
|
489
539
|
"memory.semantic.fact_id": factId
|
|
490
540
|
}, async () => {
|
|
491
|
-
await this.#store.semantic.forget(factId, reason);
|
|
541
|
+
await this.#store.semantic.forget(factId, reason, scope);
|
|
492
542
|
});
|
|
493
543
|
}
|
|
494
544
|
/**
|
|
@@ -504,7 +554,7 @@ var SemanticMemory = class {
|
|
|
504
554
|
"memory.semantic.fact_id": factId
|
|
505
555
|
}, async () => {
|
|
506
556
|
if (typeof this.#store.semantic.purge !== "function") throw new TypeError("[graphorin/memory] SemanticMemory.purge(...) requires a storage adapter that implements `semantic.purge(id)`. For storage adapters without GDPR-grade hard-delete, prefer `SemanticMemory.forget(...)`.");
|
|
507
|
-
await this.#store.semantic.purge(factId, reason);
|
|
557
|
+
await this.#store.semantic.purge(factId, reason, scope);
|
|
508
558
|
});
|
|
509
559
|
}
|
|
510
560
|
/** Fuse multiple ranked lists outside of a `search()` call. */
|
|
@@ -565,7 +615,7 @@ var SemanticMemory = class {
|
|
|
565
615
|
try {
|
|
566
616
|
const pseudo = await this.#queryTransformer.hypothetical(query, { ...opts.signal !== void 0 ? { signal: opts.signal } : {} });
|
|
567
617
|
if (pseudo === null || pseudo.trim().length === 0) return [];
|
|
568
|
-
return this.#tryVectorSearch(scope, pseudo, topK, opts.asOf, opts.includeQuarantined);
|
|
618
|
+
return this.#tryVectorSearch(scope, pseudo, topK, opts.asOf, opts.includeQuarantined, opts.includeSuperseded, opts.owner);
|
|
569
619
|
} catch {
|
|
570
620
|
return [];
|
|
571
621
|
}
|
|
@@ -661,9 +711,42 @@ var SemanticMemory = class {
|
|
|
661
711
|
if (this.#embedder === null || embedderId === null || typeof this.#store.semantic.searchVector !== "function") return [];
|
|
662
712
|
const [vector] = await this.#embedder.embed([query], { taskType: "query" });
|
|
663
713
|
if (vector === void 0) return [];
|
|
714
|
+
return this.#vectorSearchWithVector(scope, vector, topK, asOf, includeQuarantined, includeSuperseded, owner);
|
|
715
|
+
}
|
|
716
|
+
/**
|
|
717
|
+
* W-087: the store half of {@link SemanticMemory.#tryVectorSearch} -
|
|
718
|
+
* runs the KNN read against an ALREADY-COMPUTED query vector so the
|
|
719
|
+
* multi-query fan-out can batch its N variant embeddings into one
|
|
720
|
+
* `embed([q1..qN])` call instead of N provider round-trips.
|
|
721
|
+
*/
|
|
722
|
+
async #vectorSearchWithVector(scope, vector, topK, asOf, includeQuarantined, includeSuperseded, owner) {
|
|
723
|
+
const embedderId = this.#embedderIdProvider();
|
|
724
|
+
if (embedderId === null || typeof this.#store.semantic.searchVector !== "function") return [];
|
|
664
725
|
return this.#store.semantic.searchVector(scope, vector, embedderId, topK, asOf, includeQuarantined, includeSuperseded, owner);
|
|
665
726
|
}
|
|
666
727
|
/**
|
|
728
|
+
* W-087: embed every fan-out variant in ONE embedder call. Returns
|
|
729
|
+
* `null` - and the caller degrades to the per-variant path - when
|
|
730
|
+
* there is no fan-out, no vector surface, or the batch call fails; a
|
|
731
|
+
* batching failure must never fail the search.
|
|
732
|
+
*/
|
|
733
|
+
async #tryBatchEmbedQueries(queries) {
|
|
734
|
+
if (queries.length <= 1) return null;
|
|
735
|
+
if (this.#embedder === null || this.#embedderIdProvider() === null || typeof this.#store.semantic.searchVector !== "function") return null;
|
|
736
|
+
try {
|
|
737
|
+
const vectors = await this.#embedder.embed([...queries], { taskType: "query" });
|
|
738
|
+
if (vectors.length !== queries.length) return null;
|
|
739
|
+
const byQuery = /* @__PURE__ */ new Map();
|
|
740
|
+
queries.forEach((q, i) => {
|
|
741
|
+
const v = vectors[i];
|
|
742
|
+
if (v !== void 0) byQuery.set(q, v);
|
|
743
|
+
});
|
|
744
|
+
return byQuery;
|
|
745
|
+
} catch {
|
|
746
|
+
return null;
|
|
747
|
+
}
|
|
748
|
+
}
|
|
749
|
+
/**
|
|
667
750
|
* C5: multiply each hit's fused score by its trust factor and re-sort.
|
|
668
751
|
* No-ops (returns the same array) when every factor is 1.
|
|
669
752
|
*/
|