@anuma/sdk 6.43.0 → 6.43.1
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/expo/{consolidate-7WCBP5J7.mjs → consolidate-TOITBD6W.mjs} +1 -1
- package/dist/expo/index.cjs +489 -137
- package/dist/expo/index.d.mts +84 -54
- package/dist/expo/index.d.ts +84 -54
- package/dist/expo/index.mjs +478 -127
- package/dist/index.cjs +16 -8
- package/dist/index.d.mts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.mjs +14 -8
- package/dist/memory/context.d.mts +1 -0
- package/dist/memory/context.d.ts +1 -0
- package/dist/react/{consolidate-IW7EKXHN.mjs → consolidate-ZEINV2LX.mjs} +1 -1
- package/dist/react/index.cjs +316 -72
- package/dist/react/index.d.mts +83 -48
- package/dist/react/index.d.ts +83 -48
- package/dist/react/index.mjs +305 -62
- package/dist/server/{consolidate-YEGACWLR.mjs → consolidate-WY6BHODK.mjs} +1 -1
- package/dist/server/index.cjs +289 -67
- package/dist/server/index.d.mts +83 -48
- package/dist/server/index.d.ts +83 -48
- package/dist/server/index.mjs +278 -57
- package/dist/telemetry/index.d.mts +1 -0
- package/dist/telemetry/index.d.ts +1 -0
- package/dist/tools/selection/index.cjs +14 -2
- package/dist/tools/selection/index.mjs +14 -2
- package/package.json +1 -1
- package/dist/expo/{chunk-RQ3B2IYV.mjs → chunk-AF37N5Z6.mjs} +1 -1
- package/dist/react/{chunk-CERRBFF5.mjs → chunk-TGLAOFVA.mjs} +1 -1
- package/dist/server/{chunk-4RGGAOAJ.mjs → chunk-WCG5BFI6.mjs} +1 -1
package/dist/react/index.cjs
CHANGED
|
@@ -122,6 +122,18 @@ var init_logger = __esm({
|
|
|
122
122
|
}
|
|
123
123
|
});
|
|
124
124
|
|
|
125
|
+
// src/lib/taskType.ts
|
|
126
|
+
function taskTypeHeader(taskType) {
|
|
127
|
+
return taskType ? { [TASK_TYPE_HEADER]: taskType } : {};
|
|
128
|
+
}
|
|
129
|
+
var TASK_TYPE_HEADER;
|
|
130
|
+
var init_taskType = __esm({
|
|
131
|
+
"src/lib/taskType.ts"() {
|
|
132
|
+
"use strict";
|
|
133
|
+
TASK_TYPE_HEADER = "X-Anuma-Task-Type";
|
|
134
|
+
}
|
|
135
|
+
});
|
|
136
|
+
|
|
125
137
|
// src/lib/pii/patterns.ts
|
|
126
138
|
function luhnCheck(digits) {
|
|
127
139
|
let sum = 0;
|
|
@@ -766,18 +778,6 @@ var init_internalFlowMarker = __esm({
|
|
|
766
778
|
}
|
|
767
779
|
});
|
|
768
780
|
|
|
769
|
-
// src/lib/taskType.ts
|
|
770
|
-
function taskTypeHeader(taskType) {
|
|
771
|
-
return taskType ? { [TASK_TYPE_HEADER]: taskType } : {};
|
|
772
|
-
}
|
|
773
|
-
var TASK_TYPE_HEADER;
|
|
774
|
-
var init_taskType = __esm({
|
|
775
|
-
"src/lib/taskType.ts"() {
|
|
776
|
-
"use strict";
|
|
777
|
-
TASK_TYPE_HEADER = "X-Anuma-Task-Type";
|
|
778
|
-
}
|
|
779
|
-
});
|
|
780
|
-
|
|
781
781
|
// src/lib/memory/portalLlm.ts
|
|
782
782
|
function defaultBaseUrl() {
|
|
783
783
|
return typeof process !== "undefined" && process.env?.ANUMA_PORTAL_BASE_URL || BASE_URL;
|
|
@@ -7132,6 +7132,7 @@ var DEFAULT_API_EMBEDDING_MODEL = "qwen/qwen3-embedding-8b";
|
|
|
7132
7132
|
|
|
7133
7133
|
// src/lib/memoryEngine/generate.ts
|
|
7134
7134
|
init_clientConfig();
|
|
7135
|
+
init_taskType();
|
|
7135
7136
|
var EMBED_MAX_ATTEMPTS = 4;
|
|
7136
7137
|
var DEFAULT_EMBEDDING_REQUEST_TIMEOUT_MS = 15e3;
|
|
7137
7138
|
var DEFAULT_EMBEDDING_TOKEN_TIMEOUT_MS = 1e4;
|
|
@@ -7229,7 +7230,10 @@ async function embedOne(text14, options, outer) {
|
|
|
7229
7230
|
const cached = cache.get(text14);
|
|
7230
7231
|
if (cached) return Array.from(cached);
|
|
7231
7232
|
}
|
|
7232
|
-
const headers =
|
|
7233
|
+
const headers = {
|
|
7234
|
+
...await resolveAuthHeaders(options, outer),
|
|
7235
|
+
...taskTypeHeader(options.taskType)
|
|
7236
|
+
};
|
|
7233
7237
|
const response = await withEmbeddingRetry(
|
|
7234
7238
|
() => withDeadline(
|
|
7235
7239
|
(signal) => postApiV1Embeddings({
|
|
@@ -7324,7 +7328,10 @@ async function embedMany(texts, options, outer) {
|
|
|
7324
7328
|
if (uncachedTexts.length === 0) {
|
|
7325
7329
|
return results;
|
|
7326
7330
|
}
|
|
7327
|
-
const headers =
|
|
7331
|
+
const headers = {
|
|
7332
|
+
...await resolveAuthHeaders(options, outer),
|
|
7333
|
+
...taskTypeHeader(options.taskType)
|
|
7334
|
+
};
|
|
7328
7335
|
if (outer?.aborted) throw outer.reason;
|
|
7329
7336
|
const embeddingModel = model ?? DEFAULT_API_EMBEDDING_MODEL;
|
|
7330
7337
|
let newEmbeddings;
|
|
@@ -18522,6 +18529,50 @@ function applyMMR(candidates, k, lambda = 0.5) {
|
|
|
18522
18529
|
return selected;
|
|
18523
18530
|
}
|
|
18524
18531
|
|
|
18532
|
+
// src/lib/memory/recallTelemetry.ts
|
|
18533
|
+
function notifyMemoryCallback(callback, value) {
|
|
18534
|
+
try {
|
|
18535
|
+
callback?.(value);
|
|
18536
|
+
} catch {
|
|
18537
|
+
return;
|
|
18538
|
+
}
|
|
18539
|
+
}
|
|
18540
|
+
function factRecallDiagnostics(scores, elapsedMs, options = {}) {
|
|
18541
|
+
return {
|
|
18542
|
+
usedBudget: "low",
|
|
18543
|
+
reranked: false,
|
|
18544
|
+
candidateCount: options.candidateCount ?? scores.length,
|
|
18545
|
+
...options.vaultSize !== void 0 && { vaultSize: options.vaultSize },
|
|
18546
|
+
...options.decryptLast !== void 0 && { decryptLast: options.decryptLast },
|
|
18547
|
+
...options.vaultRowsDecrypted !== void 0 && {
|
|
18548
|
+
vaultRowsDecrypted: options.vaultRowsDecrypted
|
|
18549
|
+
},
|
|
18550
|
+
...options.vaultRowsEmbedded !== void 0 && {
|
|
18551
|
+
vaultRowsEmbedded: options.vaultRowsEmbedded
|
|
18552
|
+
},
|
|
18553
|
+
factCount: scores.length,
|
|
18554
|
+
chunkCount: 0,
|
|
18555
|
+
admittedCount: scores.length,
|
|
18556
|
+
topScore: scores.length ? Math.max(...scores) : -1,
|
|
18557
|
+
lowestAdmittedScore: scores.length ? Math.min(...scores) : -1,
|
|
18558
|
+
minScoreApplied: options.minScore ?? -1,
|
|
18559
|
+
truncated: options.truncated ?? false,
|
|
18560
|
+
graphLaneCount: 0,
|
|
18561
|
+
temporalLaneCount: 0,
|
|
18562
|
+
emptyReason: scores.length ? "" : options.vaultSize === 0 ? "vault-empty" : "no-candidates",
|
|
18563
|
+
timings: {
|
|
18564
|
+
total: elapsedMs,
|
|
18565
|
+
prep: 0,
|
|
18566
|
+
factLane: elapsedMs,
|
|
18567
|
+
rerank: 0,
|
|
18568
|
+
queryEmbed: options.queryEmbedMs ?? 0,
|
|
18569
|
+
chunkLane: 0,
|
|
18570
|
+
fuse: 0
|
|
18571
|
+
},
|
|
18572
|
+
degraded: options.embeddingsUnavailable ? ["embeddings-unavailable"] : []
|
|
18573
|
+
};
|
|
18574
|
+
}
|
|
18575
|
+
|
|
18525
18576
|
// src/lib/memory/recency.ts
|
|
18526
18577
|
var DAY_MS2 = 1e3 * 60 * 60 * 24;
|
|
18527
18578
|
var DEFAULT_PER_YEAR_DECAY = 0.2;
|
|
@@ -19214,6 +19265,7 @@ function rankVaultMemories(_query, queryEmbedding, items, options) {
|
|
|
19214
19265
|
}
|
|
19215
19266
|
filtered.sort((a, b) => b.similarity - a.similarity);
|
|
19216
19267
|
}
|
|
19268
|
+
notifyMemoryCallback(options?.onCandidateCount, filtered.length);
|
|
19217
19269
|
const itemById = new Map(items.map((i) => [i.id, i]));
|
|
19218
19270
|
return filtered.slice(0, limit).map((r) => resultFromItem(itemById.get(r.uniqueId), r.similarity));
|
|
19219
19271
|
}
|
|
@@ -20196,6 +20248,7 @@ async function rankPreparedVaultCandidates(query, prepared, embeddingOptions, se
|
|
|
20196
20248
|
const results = rankVaultMemories(query, queryEmbedding, embeddedItems, {
|
|
20197
20249
|
limit,
|
|
20198
20250
|
minSimilarity,
|
|
20251
|
+
onCandidateCount: searchOptions?.onCandidateCount,
|
|
20199
20252
|
...searchOptions?.supersessionBoost !== void 0 && {
|
|
20200
20253
|
supersessionBoost: searchOptions.supersessionBoost
|
|
20201
20254
|
},
|
|
@@ -20297,16 +20350,20 @@ var DEFAULT_SCOPE = "private";
|
|
|
20297
20350
|
var DEFAULT_CONSOLIDATE_THRESHOLD = 0.55;
|
|
20298
20351
|
var DEFAULT_CONSOLIDATE_TOP_K = 20;
|
|
20299
20352
|
async function retain(content, ctx, options = {}) {
|
|
20353
|
+
const embeddingOptions = {
|
|
20354
|
+
...ctx.embeddingOptions,
|
|
20355
|
+
taskType: "memory_retain_embed"
|
|
20356
|
+
};
|
|
20300
20357
|
return retainWithPersistence(
|
|
20301
20358
|
content,
|
|
20302
20359
|
{
|
|
20303
|
-
embeddingOptions
|
|
20360
|
+
embeddingOptions,
|
|
20304
20361
|
vaultCache: ctx.vaultCache,
|
|
20305
20362
|
persistence: {
|
|
20306
20363
|
prepare: (query, searchOptions) => prepareVaultCandidates(
|
|
20307
20364
|
query,
|
|
20308
20365
|
ctx.vaultCtx,
|
|
20309
|
-
|
|
20366
|
+
embeddingOptions,
|
|
20310
20367
|
ctx.vaultCache,
|
|
20311
20368
|
searchOptions
|
|
20312
20369
|
),
|
|
@@ -21460,7 +21517,17 @@ function parseVerdict(parsed) {
|
|
|
21460
21517
|
|
|
21461
21518
|
// src/lib/memory/decayWorker.ts
|
|
21462
21519
|
init_logger();
|
|
21463
|
-
|
|
21520
|
+
function emptyResult() {
|
|
21521
|
+
return {
|
|
21522
|
+
archived: 0,
|
|
21523
|
+
deleted: 0,
|
|
21524
|
+
scanned: 0,
|
|
21525
|
+
ruleDriven: { archived: 0, deleted: 0 },
|
|
21526
|
+
classifierDriven: { archived: 0, deleted: 0 },
|
|
21527
|
+
classifierCalls: 0,
|
|
21528
|
+
classifierCapHits: 0
|
|
21529
|
+
};
|
|
21530
|
+
}
|
|
21464
21531
|
var DEFAULT_MAX_CLASSIFIER_CALLS_PER_SWEEP = 20;
|
|
21465
21532
|
function resolveNow(now) {
|
|
21466
21533
|
if (typeof now === "function") return now();
|
|
@@ -21499,42 +21566,45 @@ function createDecaySweeper(options) {
|
|
|
21499
21566
|
let disposed = false;
|
|
21500
21567
|
async function verdictFor(input, now, sweep) {
|
|
21501
21568
|
const ruleVerdict = classifyDecay(input, now, policy);
|
|
21502
|
-
|
|
21503
|
-
if (
|
|
21569
|
+
const rule = { verdict: ruleVerdict, source: "ruleDriven" };
|
|
21570
|
+
if (ruleVerdict !== "keep") return rule;
|
|
21571
|
+
if (!classifier || !isBorderline(input)) return rule;
|
|
21504
21572
|
if (input.id) {
|
|
21505
21573
|
const cached = classifierCache.get(input.id);
|
|
21506
|
-
if (cached && cached.activityAt === lastActivityAt(input))
|
|
21574
|
+
if (cached && cached.activityAt === lastActivityAt(input))
|
|
21575
|
+
return { verdict: cached.verdict, source: "classifierDriven" };
|
|
21507
21576
|
}
|
|
21508
21577
|
if (sweep.classifierCalls >= maxClassifierCalls) {
|
|
21578
|
+
sweep.classifierCapHits++;
|
|
21509
21579
|
if (!sweep.ceilingLogged) {
|
|
21510
21580
|
sweep.ceilingLogged = true;
|
|
21511
21581
|
getLogger().warn(
|
|
21512
21582
|
`[memory/decay] classifier per-sweep ceiling (${maxClassifierCalls}) reached; remaining borderline rows use the rule verdict this sweep`
|
|
21513
21583
|
);
|
|
21514
21584
|
}
|
|
21515
|
-
return
|
|
21585
|
+
return rule;
|
|
21516
21586
|
}
|
|
21517
21587
|
sweep.classifierCalls++;
|
|
21518
21588
|
try {
|
|
21519
21589
|
const verdict = await classifier.classify(input, ruleVerdict, now);
|
|
21520
21590
|
if (input.id) classifierCache.set(input.id, { activityAt: lastActivityAt(input), verdict });
|
|
21521
|
-
return verdict;
|
|
21591
|
+
return { verdict, source: "classifierDriven" };
|
|
21522
21592
|
} catch (err) {
|
|
21523
21593
|
getLogger().warn(
|
|
21524
21594
|
`[memory/decay] classifier failed; falling back to rule verdict: ${err instanceof Error ? err.message : String(err)}`
|
|
21525
21595
|
);
|
|
21526
|
-
return
|
|
21596
|
+
return rule;
|
|
21527
21597
|
}
|
|
21528
21598
|
}
|
|
21529
21599
|
async function runSweep() {
|
|
21530
|
-
if (disposed) return
|
|
21600
|
+
if (disposed) return emptyResult();
|
|
21531
21601
|
const now = resolveNow(options.now);
|
|
21532
21602
|
let candidates;
|
|
21533
21603
|
try {
|
|
21534
21604
|
candidates = await getDecayCandidatesRawOp(vaultCtx);
|
|
21535
21605
|
} catch (err) {
|
|
21536
21606
|
onError?.(err instanceof Error ? err : new Error(String(err)));
|
|
21537
|
-
return
|
|
21607
|
+
return emptyResult();
|
|
21538
21608
|
}
|
|
21539
21609
|
if (classifierCache.size > 0) {
|
|
21540
21610
|
const liveIds = new Set(candidates.map((c) => c.uniqueId));
|
|
@@ -21542,33 +21612,40 @@ function createDecaySweeper(options) {
|
|
|
21542
21612
|
if (!liveIds.has(id)) classifierCache.delete(id);
|
|
21543
21613
|
}
|
|
21544
21614
|
}
|
|
21545
|
-
const sweep = { classifierCalls: 0, ceilingLogged: false };
|
|
21615
|
+
const sweep = { classifierCalls: 0, classifierCapHits: 0, ceilingLogged: false };
|
|
21546
21616
|
const toArchive = [];
|
|
21547
21617
|
const toDelete = [];
|
|
21548
21618
|
for (const c of candidates) {
|
|
21549
|
-
const verdict = await verdictFor(toDecayInput(c), now, sweep);
|
|
21550
|
-
if (verdict === "archive") toArchive.push(c);
|
|
21551
|
-
else if (verdict === "delete") toDelete.push(c);
|
|
21552
|
-
}
|
|
21553
|
-
|
|
21554
|
-
|
|
21619
|
+
const { verdict, source } = await verdictFor(toDecayInput(c), now, sweep);
|
|
21620
|
+
if (verdict === "archive") toArchive.push({ candidate: c, source });
|
|
21621
|
+
else if (verdict === "delete") toDelete.push({ candidate: c, source });
|
|
21622
|
+
}
|
|
21623
|
+
const result = emptyResult();
|
|
21624
|
+
result.scanned = candidates.length;
|
|
21625
|
+
result.classifierCalls = sweep.classifierCalls;
|
|
21626
|
+
result.classifierCapHits = sweep.classifierCapHits;
|
|
21555
21627
|
try {
|
|
21556
|
-
for (const c of toArchive) {
|
|
21628
|
+
for (const { candidate: c, source } of toArchive) {
|
|
21557
21629
|
const ok = await archiveVaultMemoryOp(vaultCtx, c.uniqueId, {
|
|
21558
21630
|
now,
|
|
21559
21631
|
expectedUpdatedAt: c.updatedAt,
|
|
21560
21632
|
expectedLastObservedAt: c.lastObservedAt ?? null
|
|
21561
21633
|
});
|
|
21562
|
-
if (ok)
|
|
21634
|
+
if (ok) {
|
|
21635
|
+
result.archived++;
|
|
21636
|
+
result[source].archived++;
|
|
21637
|
+
}
|
|
21563
21638
|
}
|
|
21564
|
-
for (const c of toDelete) {
|
|
21639
|
+
for (const { candidate: c, source } of toDelete) {
|
|
21565
21640
|
const ok = await hardDeleteDecayedOp(vaultCtx, c.uniqueId, { hardDeleteWindowMs, now });
|
|
21566
|
-
if (ok)
|
|
21641
|
+
if (ok) {
|
|
21642
|
+
result.deleted++;
|
|
21643
|
+
result[source].deleted++;
|
|
21644
|
+
}
|
|
21567
21645
|
}
|
|
21568
21646
|
} catch (err) {
|
|
21569
21647
|
onError?.(err instanceof Error ? err : new Error(String(err)));
|
|
21570
21648
|
}
|
|
21571
|
-
const result = { archived, deleted, scanned: candidates.length };
|
|
21572
21649
|
onSwept?.(result);
|
|
21573
21650
|
return result;
|
|
21574
21651
|
}
|
|
@@ -22173,6 +22250,10 @@ async function recall(query, ctx, options = {}) {
|
|
|
22173
22250
|
const flags = flagsForBudget(usedBudget);
|
|
22174
22251
|
const normalizedFacets = normalizeSubQueries(options.subQueries);
|
|
22175
22252
|
const subQueries = normalizedFacets.length >= 2 ? normalizedFacets : void 0;
|
|
22253
|
+
const embeddingOptions = {
|
|
22254
|
+
...ctx.embeddingOptions,
|
|
22255
|
+
taskType: "memory_recall_embed"
|
|
22256
|
+
};
|
|
22176
22257
|
const t0 = nowMs2();
|
|
22177
22258
|
let prepMs = 0;
|
|
22178
22259
|
let factLaneMs = 0;
|
|
@@ -22268,7 +22349,7 @@ async function recall(query, ctx, options = {}) {
|
|
|
22268
22349
|
let sharedEmbedMs = 0;
|
|
22269
22350
|
const [queryEmbedding, entityRanking, temporalRanking] = await Promise.all([
|
|
22270
22351
|
needsChunkEmbedding ? generateEmbedding(query, {
|
|
22271
|
-
...
|
|
22352
|
+
...embeddingOptions,
|
|
22272
22353
|
totalTimeoutMs: queryEmbedTotalTimeoutMs
|
|
22273
22354
|
}).finally(() => {
|
|
22274
22355
|
sharedEmbedMs = nowMs2() - prepStart;
|
|
@@ -22326,7 +22407,7 @@ async function recall(query, ctx, options = {}) {
|
|
|
22326
22407
|
} = await (ctx.factSource?.search.bind(ctx.factSource) ?? ((searchQuery, searchOptions) => searchVaultMemoriesWithSize(
|
|
22327
22408
|
searchQuery,
|
|
22328
22409
|
ctx.vaultCtx,
|
|
22329
|
-
|
|
22410
|
+
embeddingOptions,
|
|
22330
22411
|
ctx.vaultCache,
|
|
22331
22412
|
searchOptions
|
|
22332
22413
|
)))(query, {
|
|
@@ -22692,7 +22773,7 @@ function isDumpQuery(query) {
|
|
|
22692
22773
|
async function listRecentFacts(ctx, limit, toolOptions) {
|
|
22693
22774
|
const store = toolOptions?.memoryStore;
|
|
22694
22775
|
const vaultCtx = ctx.vaultCtx;
|
|
22695
|
-
if (!vaultCtx && !store) return [];
|
|
22776
|
+
if (!vaultCtx && !store) return { memories: [], truncated: false };
|
|
22696
22777
|
const read = (ids) => store ? store.list({ memoryIds: ids }) : getVaultMemoriesByIdsOp(vaultCtx, ids);
|
|
22697
22778
|
const filters = {
|
|
22698
22779
|
...toolOptions?.scopes && { scopes: toolOptions.scopes },
|
|
@@ -22703,34 +22784,47 @@ async function listRecentFacts(ctx, limit, toolOptions) {
|
|
|
22703
22784
|
...toolOptions?.folderId !== void 0 && { folderId: toolOptions.folderId }
|
|
22704
22785
|
});
|
|
22705
22786
|
const readable = [];
|
|
22787
|
+
const readLimit = limit + 1;
|
|
22788
|
+
let batchLimit = limit;
|
|
22706
22789
|
let start = 0;
|
|
22707
|
-
|
|
22790
|
+
let projected = 0;
|
|
22791
|
+
let exhausted = false;
|
|
22792
|
+
for (let size = readLimit; readable.length < readLimit; size *= 2) {
|
|
22708
22793
|
const ordered = await project(size);
|
|
22709
|
-
|
|
22710
|
-
|
|
22794
|
+
projected = ordered.length;
|
|
22795
|
+
exhausted = !store || ordered.length < size;
|
|
22796
|
+
for (let i = start; i < ordered.length && readable.length < readLimit; ) {
|
|
22797
|
+
const batch = ordered.slice(i, i + batchLimit).map((p) => p.uniqueId);
|
|
22711
22798
|
const byId = new Map((await read(batch)).map((m) => [m.uniqueId, m]));
|
|
22799
|
+
const previousCount = readable.length;
|
|
22712
22800
|
for (const id of batch) {
|
|
22713
22801
|
const m = byId.get(id);
|
|
22714
22802
|
if (m && !isEncrypted(m.content)) readable.push(m);
|
|
22715
|
-
if (readable.length >=
|
|
22803
|
+
if (readable.length >= readLimit) break;
|
|
22716
22804
|
}
|
|
22805
|
+
batchLimit = readable.length > previousCount ? Math.min(limit, readLimit - readable.length) : limit;
|
|
22806
|
+
i += batch.length;
|
|
22717
22807
|
}
|
|
22718
|
-
if (
|
|
22808
|
+
if (exhausted) break;
|
|
22719
22809
|
start = ordered.length;
|
|
22720
22810
|
}
|
|
22721
|
-
return
|
|
22722
|
-
|
|
22723
|
-
|
|
22724
|
-
|
|
22725
|
-
|
|
22726
|
-
|
|
22727
|
-
|
|
22728
|
-
|
|
22729
|
-
|
|
22730
|
-
|
|
22731
|
-
|
|
22732
|
-
|
|
22733
|
-
|
|
22811
|
+
return {
|
|
22812
|
+
memories: readable.slice(0, limit).map((m) => ({
|
|
22813
|
+
id: m.uniqueId,
|
|
22814
|
+
kind: "fact",
|
|
22815
|
+
content: m.content,
|
|
22816
|
+
score: 0,
|
|
22817
|
+
folderId: m.folderId,
|
|
22818
|
+
eventTimeStart: m.eventTimeStart,
|
|
22819
|
+
eventTimeEnd: m.eventTimeEnd,
|
|
22820
|
+
eventTimeKind: m.eventTimeKind,
|
|
22821
|
+
factType: m.factType,
|
|
22822
|
+
createdAt: m.createdAt,
|
|
22823
|
+
updatedAt: m.updatedAt
|
|
22824
|
+
})),
|
|
22825
|
+
...exhausted && { vaultSize: projected },
|
|
22826
|
+
truncated: readable.length > limit
|
|
22827
|
+
};
|
|
22734
22828
|
}
|
|
22735
22829
|
function createRecallTool(ctx, toolOptions, callbacks) {
|
|
22736
22830
|
if (toolOptions?.memoryStore && toolOptions.folderId !== void 0)
|
|
@@ -22769,7 +22863,11 @@ function createRecallTool(ctx, toolOptions, callbacks) {
|
|
|
22769
22863
|
},
|
|
22770
22864
|
executor: async (args) => {
|
|
22771
22865
|
if (typeof args.query !== "string" || args.query.length === 0) {
|
|
22772
|
-
|
|
22866
|
+
const error = new Error(
|
|
22867
|
+
"recall_memory: `query` is required and must be a non-empty string."
|
|
22868
|
+
);
|
|
22869
|
+
notifyMemoryCallback(callbacks?.onError, error);
|
|
22870
|
+
throw error;
|
|
22773
22871
|
}
|
|
22774
22872
|
const query = args.query;
|
|
22775
22873
|
const now = Date.now();
|
|
@@ -22797,10 +22895,17 @@ function createRecallTool(ctx, toolOptions, callbacks) {
|
|
|
22797
22895
|
RECALL_MAX_MEMORIES_PER_CONVERSATION - conversationMemories
|
|
22798
22896
|
);
|
|
22799
22897
|
const effectiveLimit = Math.min(requestLimit, remainingTurnBudget, remainingConvBudget);
|
|
22898
|
+
const truncatedByBudget = effectiveLimit < requestLimit;
|
|
22899
|
+
if (truncatedByBudget) {
|
|
22900
|
+
notifyMemoryCallback(callbacks?.onTruncated, {
|
|
22901
|
+
requestedLimit: requestLimit,
|
|
22902
|
+
effectiveLimit,
|
|
22903
|
+
truncatedByBudget
|
|
22904
|
+
});
|
|
22905
|
+
}
|
|
22800
22906
|
if (effectiveLimit <= 0) {
|
|
22801
22907
|
return VOLUME_LIMIT_NOTICE;
|
|
22802
22908
|
}
|
|
22803
|
-
const truncatedByBudget = effectiveLimit < requestLimit;
|
|
22804
22909
|
turnMemories += effectiveLimit;
|
|
22805
22910
|
conversationMemories += effectiveLimit;
|
|
22806
22911
|
let surfaced = 0;
|
|
@@ -22809,7 +22914,27 @@ function createRecallTool(ctx, toolOptions, callbacks) {
|
|
|
22809
22914
|
const wantsRecent = args.sort === "recent" && defaultTypes.includes("fact") && (ctx.vaultCtx !== void 0 || toolOptions?.memoryStore !== void 0);
|
|
22810
22915
|
let result;
|
|
22811
22916
|
if (wantsRecent) {
|
|
22812
|
-
|
|
22917
|
+
const start = Date.now();
|
|
22918
|
+
const recent = await listRecentFacts(ctx, effectiveLimit, toolOptions);
|
|
22919
|
+
result = recent;
|
|
22920
|
+
notifyMemoryCallback(callbacks?.onDiagnostics, {
|
|
22921
|
+
...factRecallDiagnostics(
|
|
22922
|
+
result.memories.map((m) => m.score),
|
|
22923
|
+
Date.now() - start,
|
|
22924
|
+
{
|
|
22925
|
+
truncated: recent.truncated,
|
|
22926
|
+
...recent.vaultSize !== void 0 && { vaultSize: recent.vaultSize }
|
|
22927
|
+
}
|
|
22928
|
+
),
|
|
22929
|
+
truncatedByBudget
|
|
22930
|
+
});
|
|
22931
|
+
if (recent.truncated && !truncatedByBudget) {
|
|
22932
|
+
notifyMemoryCallback(callbacks?.onTruncated, {
|
|
22933
|
+
requestedLimit: requestLimit,
|
|
22934
|
+
effectiveLimit,
|
|
22935
|
+
truncatedByBudget
|
|
22936
|
+
});
|
|
22937
|
+
}
|
|
22813
22938
|
} else {
|
|
22814
22939
|
let subQueries;
|
|
22815
22940
|
if (defaultBudget === "high" && toolOptions?.decomposeOptions) {
|
|
@@ -22821,6 +22946,14 @@ function createRecallTool(ctx, toolOptions, callbacks) {
|
|
|
22821
22946
|
const recallOpts = {
|
|
22822
22947
|
onDiagnostics: (d) => {
|
|
22823
22948
|
recallDegraded = d.degraded;
|
|
22949
|
+
notifyMemoryCallback(callbacks?.onDiagnostics, { ...d, truncatedByBudget });
|
|
22950
|
+
if (d.truncated && !truncatedByBudget) {
|
|
22951
|
+
notifyMemoryCallback(callbacks?.onTruncated, {
|
|
22952
|
+
requestedLimit: requestLimit,
|
|
22953
|
+
effectiveLimit,
|
|
22954
|
+
truncatedByBudget
|
|
22955
|
+
});
|
|
22956
|
+
}
|
|
22824
22957
|
},
|
|
22825
22958
|
types: defaultTypes,
|
|
22826
22959
|
limit: effectiveLimit,
|
|
@@ -22864,6 +22997,7 @@ ${TRUNCATION_NOTICE}` : formatted;
|
|
|
22864
22997
|
const message = error instanceof Error ? error.message : "Unknown error";
|
|
22865
22998
|
const wrapped = new Error(`recall_memory: search failed \u2014 ${message}`);
|
|
22866
22999
|
wrapped.cause = error;
|
|
23000
|
+
notifyMemoryCallback(callbacks?.onError, wrapped);
|
|
22867
23001
|
throw wrapped;
|
|
22868
23002
|
} finally {
|
|
22869
23003
|
const unused = effectiveLimit - surfaced;
|
|
@@ -23105,6 +23239,18 @@ When a memory refers to one of these, reuse the EXACT existing name (same spelli
|
|
|
23105
23239
|
` : "";
|
|
23106
23240
|
for (let i = 0; i < memories.length; i += TOPIC_EXTRACTION_BATCH_SIZE) {
|
|
23107
23241
|
const batch = memories.slice(i, i + TOPIC_EXTRACTION_BATCH_SIZE);
|
|
23242
|
+
const start = Date.now();
|
|
23243
|
+
let attempts = 0;
|
|
23244
|
+
let failure;
|
|
23245
|
+
const reportBatch = (unansweredCount) => {
|
|
23246
|
+
notifyMemoryCallback(options.onBatch, {
|
|
23247
|
+
memoryIds: batch.map((m) => m.id),
|
|
23248
|
+
attempts,
|
|
23249
|
+
durationMs: Date.now() - start,
|
|
23250
|
+
unansweredCount,
|
|
23251
|
+
...failure && { failure }
|
|
23252
|
+
});
|
|
23253
|
+
};
|
|
23108
23254
|
const rows = [];
|
|
23109
23255
|
for (const m of batch) {
|
|
23110
23256
|
const content = m.content.slice(0, MAX_CHARS_PER_MEMORY).replace(/\s+/g, " ").trim();
|
|
@@ -23126,6 +23272,12 @@ ${listing}
|
|
|
23126
23272
|
|
|
23127
23273
|
List each memory's named entities.`,
|
|
23128
23274
|
tag: "memory/topics",
|
|
23275
|
+
onAttempt: (attempt) => {
|
|
23276
|
+
attempts = attempt.attempt;
|
|
23277
|
+
},
|
|
23278
|
+
onFailure: (value) => {
|
|
23279
|
+
failure = value;
|
|
23280
|
+
},
|
|
23129
23281
|
extra: { max_completion_tokens: MAX_COMPLETION_TOKENS },
|
|
23130
23282
|
...options.fetchFn && { fetchFn: options.fetchFn },
|
|
23131
23283
|
...options.maxAttempts !== void 0 && { maxAttempts: options.maxAttempts },
|
|
@@ -23134,6 +23286,7 @@ List each memory's named entities.`,
|
|
|
23134
23286
|
...options.backoffMs && { backoffMs: options.backoffMs }
|
|
23135
23287
|
});
|
|
23136
23288
|
if (parsed === null) {
|
|
23289
|
+
reportBatch(batch.length);
|
|
23137
23290
|
getLogger().warn(
|
|
23138
23291
|
`[memory/topics] batch of ${batch.length} failed after retries \u2014 will retry next sweep`
|
|
23139
23292
|
);
|
|
@@ -23142,6 +23295,7 @@ List each memory's named entities.`,
|
|
|
23142
23295
|
const validIds = new Set(batch.map((m) => m.id));
|
|
23143
23296
|
const byId = parseTopicResponse(parsed, validIds);
|
|
23144
23297
|
if (byId === null) {
|
|
23298
|
+
reportBatch(batch.length);
|
|
23145
23299
|
getLogger().warn(
|
|
23146
23300
|
`[memory/topics] batch of ${batch.length} returned an unrecognized shape \u2014 will retry next sweep`
|
|
23147
23301
|
);
|
|
@@ -23154,6 +23308,7 @@ List each memory's named entities.`,
|
|
|
23154
23308
|
}
|
|
23155
23309
|
out.set(m.id, redactor ? restoreEntities(entities, redactor) : entities);
|
|
23156
23310
|
}
|
|
23311
|
+
reportBatch(batch.filter((m) => !byId.has(m.id)).length);
|
|
23157
23312
|
}
|
|
23158
23313
|
return out;
|
|
23159
23314
|
}
|
|
@@ -23192,6 +23347,7 @@ function isDegradedTopicSkip(reason) {
|
|
|
23192
23347
|
return DEGRADED_TOPIC_SKIP[reason] === true;
|
|
23193
23348
|
}
|
|
23194
23349
|
async function extractAndLinkEntitiesForMemoriesOp(ctx, memoryIds, options) {
|
|
23350
|
+
const start = Date.now();
|
|
23195
23351
|
const entityCtx = ctx.entityCtx;
|
|
23196
23352
|
if (!entityCtx) {
|
|
23197
23353
|
throw new Error("extractAndLinkEntitiesForMemoriesOp requires ctx.entityCtx");
|
|
@@ -23232,7 +23388,18 @@ async function extractAndLinkEntitiesForMemoriesOp(ctx, memoryIds, options) {
|
|
|
23232
23388
|
skip(id, "unreadable");
|
|
23233
23389
|
}
|
|
23234
23390
|
}
|
|
23235
|
-
const
|
|
23391
|
+
const batches = [];
|
|
23392
|
+
const llmFailures = /* @__PURE__ */ new Map();
|
|
23393
|
+
const entitiesByMemory = await extractEntitiesForMemories(inputs, {
|
|
23394
|
+
...options,
|
|
23395
|
+
onBatch: (batch) => {
|
|
23396
|
+
batches.push(batch);
|
|
23397
|
+
if (batch.failure) {
|
|
23398
|
+
for (const id of batch.memoryIds) llmFailures.set(id, batch.failure);
|
|
23399
|
+
}
|
|
23400
|
+
notifyMemoryCallback(options.onBatch, batch);
|
|
23401
|
+
}
|
|
23402
|
+
});
|
|
23236
23403
|
const toStamp = [];
|
|
23237
23404
|
for (const input of inputs) {
|
|
23238
23405
|
const entities = entitiesByMemory.get(input.id);
|
|
@@ -23263,7 +23430,16 @@ async function extractAndLinkEntitiesForMemoriesOp(ctx, memoryIds, options) {
|
|
|
23263
23430
|
entitiesByMemory.delete(id);
|
|
23264
23431
|
}
|
|
23265
23432
|
}
|
|
23266
|
-
return {
|
|
23433
|
+
return {
|
|
23434
|
+
entitiesByMemory,
|
|
23435
|
+
stampedIds,
|
|
23436
|
+
skippedIds,
|
|
23437
|
+
skippedReasons,
|
|
23438
|
+
batchCount: batches.length,
|
|
23439
|
+
durationMs: Date.now() - start,
|
|
23440
|
+
batches,
|
|
23441
|
+
llmFailures
|
|
23442
|
+
};
|
|
23267
23443
|
}
|
|
23268
23444
|
|
|
23269
23445
|
// src/lib/memory/store/local.ts
|
|
@@ -23418,7 +23594,7 @@ function createLocalMemoryStore(options) {
|
|
|
23418
23594
|
search: (query, searchOptions) => searchVaultMemoriesWithSize(
|
|
23419
23595
|
query,
|
|
23420
23596
|
vaultCtx,
|
|
23421
|
-
options.embeddingOptions,
|
|
23597
|
+
{ ...options.embeddingOptions, taskType: "memory_recall_embed" },
|
|
23422
23598
|
vaultCache,
|
|
23423
23599
|
searchOptions
|
|
23424
23600
|
),
|
|
@@ -24082,6 +24258,7 @@ function createRemoteMemoryPipeline(options) {
|
|
|
24082
24258
|
const budgetMs = search.queryEmbedTotalTimeoutMs ?? 8e3;
|
|
24083
24259
|
const embed = (texts) => generateEmbeddings(texts, {
|
|
24084
24260
|
...embeddingOptions,
|
|
24261
|
+
taskType: mode === "retain" ? "memory_retain_embed" : "memory_recall_embed",
|
|
24085
24262
|
totalTimeoutMs: budgetMs
|
|
24086
24263
|
});
|
|
24087
24264
|
const embedFacets = async () => {
|
|
@@ -24330,7 +24507,7 @@ function createRemoteMemoryPipeline(options) {
|
|
|
24330
24507
|
const ranked = await rankPreparedVaultCandidates(
|
|
24331
24508
|
text14,
|
|
24332
24509
|
prepared,
|
|
24333
|
-
embeddingOptions,
|
|
24510
|
+
{ ...embeddingOptions, taskType: "memory_recall_embed" },
|
|
24334
24511
|
searchOptions
|
|
24335
24512
|
);
|
|
24336
24513
|
return {
|
|
@@ -24352,7 +24529,7 @@ function createRemoteMemoryPipeline(options) {
|
|
|
24352
24529
|
content,
|
|
24353
24530
|
{
|
|
24354
24531
|
persistence: port,
|
|
24355
|
-
embeddingOptions,
|
|
24532
|
+
embeddingOptions: { ...embeddingOptions, taskType: "memory_retain_embed" },
|
|
24356
24533
|
vaultCache: /* @__PURE__ */ new Map(),
|
|
24357
24534
|
normalizeEmbedding: storedVector
|
|
24358
24535
|
},
|
|
@@ -25081,7 +25258,8 @@ function createRemoteMemoryStore(options) {
|
|
|
25081
25258
|
};
|
|
25082
25259
|
},
|
|
25083
25260
|
extractTopics: async (memoryIds, extractOptions) => {
|
|
25084
|
-
const
|
|
25261
|
+
const start = Date.now();
|
|
25262
|
+
const extractedAt = extractOptions.now ?? start;
|
|
25085
25263
|
const skippedIds = [];
|
|
25086
25264
|
const skippedReasons = /* @__PURE__ */ new Map();
|
|
25087
25265
|
const skip = (id, reason) => {
|
|
@@ -25099,7 +25277,18 @@ function createRemoteMemoryStore(options) {
|
|
|
25099
25277
|
else if (memory.is_deleted || memory.topics_user_managed) skip(id, "excluded");
|
|
25100
25278
|
else inputs.push({ id, content: memory.content });
|
|
25101
25279
|
}
|
|
25102
|
-
const
|
|
25280
|
+
const batches = [];
|
|
25281
|
+
const llmFailures = /* @__PURE__ */ new Map();
|
|
25282
|
+
const entitiesByMemory = await extractEntitiesForMemories(inputs, {
|
|
25283
|
+
...extractOptions,
|
|
25284
|
+
onBatch: (batch) => {
|
|
25285
|
+
batches.push(batch);
|
|
25286
|
+
if (batch.failure) {
|
|
25287
|
+
for (const id of batch.memoryIds) llmFailures.set(id, batch.failure);
|
|
25288
|
+
}
|
|
25289
|
+
notifyMemoryCallback(extractOptions.onBatch, batch);
|
|
25290
|
+
}
|
|
25291
|
+
});
|
|
25103
25292
|
const answered = /* @__PURE__ */ new Map();
|
|
25104
25293
|
for (const input of inputs) {
|
|
25105
25294
|
const entities = entitiesByMemory.get(input.id);
|
|
@@ -25148,7 +25337,16 @@ function createRemoteMemoryStore(options) {
|
|
|
25148
25337
|
getLogger().warn("[memory/remote-store] Failed to write extracted topics:", error);
|
|
25149
25338
|
for (const id of answered.keys()) fail(id, "link-failed");
|
|
25150
25339
|
}
|
|
25151
|
-
return {
|
|
25340
|
+
return {
|
|
25341
|
+
entitiesByMemory,
|
|
25342
|
+
stampedIds,
|
|
25343
|
+
skippedIds,
|
|
25344
|
+
skippedReasons,
|
|
25345
|
+
batchCount: batches.length,
|
|
25346
|
+
durationMs: Date.now() - start,
|
|
25347
|
+
batches,
|
|
25348
|
+
llmFailures
|
|
25349
|
+
};
|
|
25152
25350
|
},
|
|
25153
25351
|
stampTopicsExtracted: async (memoryIds, extractedAt, version = TOPICS_EXTRACTION_VERSION) => {
|
|
25154
25352
|
const ids = [...new Set(memoryIds)];
|
|
@@ -27164,9 +27362,13 @@ function formatVaultHits(hits) {
|
|
|
27164
27362
|
return hits.map((h, i) => `[${i + 1}] (id: ${h.id}, similarity: ${h.score.toFixed(2)})
|
|
27165
27363
|
${h.content}`).join("\n\n");
|
|
27166
27364
|
}
|
|
27167
|
-
function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOptions) {
|
|
27365
|
+
function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOptions, callbacks) {
|
|
27168
27366
|
const limit = searchOptions?.limit ?? 5;
|
|
27169
27367
|
const minSimilarity = searchOptions?.minSimilarity ?? 0.1;
|
|
27368
|
+
const recallEmbeddingOptions = {
|
|
27369
|
+
...embeddingOptions,
|
|
27370
|
+
taskType: "memory_recall_embed"
|
|
27371
|
+
};
|
|
27170
27372
|
const tuningForward = {
|
|
27171
27373
|
...searchOptions?.rerankTopN !== void 0 && { rerankTopN: searchOptions.rerankTopN },
|
|
27172
27374
|
...searchOptions?.ceWeight !== void 0 && { ceWeight: searchOptions.ceWeight },
|
|
@@ -27220,6 +27422,7 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
|
|
|
27220
27422
|
const requestLimit = Number.isFinite(rawLimit) ? Math.min(Math.max(Math.floor(rawLimit), 1), RECALL_MAX_LIMIT) : limit;
|
|
27221
27423
|
const argFolderId = args.folder_id;
|
|
27222
27424
|
if (!query || typeof query !== "string") {
|
|
27425
|
+
notifyMemoryCallback(callbacks?.onError, new Error("A search query is required."));
|
|
27223
27426
|
return "Error: A search query is required.";
|
|
27224
27427
|
}
|
|
27225
27428
|
try {
|
|
@@ -27227,7 +27430,11 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
|
|
|
27227
27430
|
const budget = wantsDecompose ? "high" : searchOptions?.rerank ? "mid" : "low";
|
|
27228
27431
|
const folderId = searchOptions?.folderId ?? argFolderId;
|
|
27229
27432
|
if (searchOptions?.useFusion === false) {
|
|
27433
|
+
let candidateCount;
|
|
27230
27434
|
const legacyOptions = {
|
|
27435
|
+
onCandidateCount: (count2) => {
|
|
27436
|
+
candidateCount = count2;
|
|
27437
|
+
},
|
|
27231
27438
|
limit: requestLimit,
|
|
27232
27439
|
minSimilarity,
|
|
27233
27440
|
useFusion: false,
|
|
@@ -27235,13 +27442,38 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
|
|
|
27235
27442
|
...folderId !== void 0 && { folderId },
|
|
27236
27443
|
...searchOptions?.scopes && { scopes: searchOptions.scopes }
|
|
27237
27444
|
};
|
|
27238
|
-
const
|
|
27445
|
+
const start = Date.now();
|
|
27446
|
+
const outcome2 = "retain" in vaultCtx ? await vaultCtx.factSource.search(query, legacyOptions) : await searchVaultMemoriesWithSize(
|
|
27239
27447
|
query,
|
|
27240
27448
|
vaultCtx,
|
|
27241
|
-
|
|
27449
|
+
recallEmbeddingOptions,
|
|
27242
27450
|
cache,
|
|
27243
27451
|
legacyOptions
|
|
27244
27452
|
);
|
|
27453
|
+
const { results: legacy, embeddingsUnavailable, vaultSize } = outcome2;
|
|
27454
|
+
const diagnostics = factRecallDiagnostics(
|
|
27455
|
+
legacy.map((m) => m.similarity),
|
|
27456
|
+
Date.now() - start,
|
|
27457
|
+
{
|
|
27458
|
+
vaultSize,
|
|
27459
|
+
minScore: minSimilarity,
|
|
27460
|
+
embeddingsUnavailable,
|
|
27461
|
+
candidateCount,
|
|
27462
|
+
truncated: candidateCount !== void 0 && candidateCount > requestLimit,
|
|
27463
|
+
decryptLast: outcome2.decryptLast,
|
|
27464
|
+
vaultRowsDecrypted: outcome2.rowsDecrypted,
|
|
27465
|
+
vaultRowsEmbedded: outcome2.rowsEmbedded,
|
|
27466
|
+
queryEmbedMs: outcome2.queryEmbedMs
|
|
27467
|
+
}
|
|
27468
|
+
);
|
|
27469
|
+
notifyMemoryCallback(callbacks?.onDiagnostics, diagnostics);
|
|
27470
|
+
if (diagnostics.truncated) {
|
|
27471
|
+
notifyMemoryCallback(callbacks?.onTruncated, {
|
|
27472
|
+
requestedLimit: requestLimit,
|
|
27473
|
+
effectiveLimit: requestLimit,
|
|
27474
|
+
truncatedByBudget: false
|
|
27475
|
+
});
|
|
27476
|
+
}
|
|
27245
27477
|
if (legacy.length === 0) {
|
|
27246
27478
|
return embeddingsUnavailable ? EMBEDDINGS_DEGRADED_EMPTY_NO_LEXICAL : "No relevant memories found in the vault.";
|
|
27247
27479
|
}
|
|
@@ -27263,6 +27495,14 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
|
|
|
27263
27495
|
{
|
|
27264
27496
|
onDiagnostics: (d) => {
|
|
27265
27497
|
recallDegraded = d.degraded;
|
|
27498
|
+
notifyMemoryCallback(callbacks?.onDiagnostics, d);
|
|
27499
|
+
if (d.truncated) {
|
|
27500
|
+
notifyMemoryCallback(callbacks?.onTruncated, {
|
|
27501
|
+
requestedLimit: requestLimit,
|
|
27502
|
+
effectiveLimit: requestLimit,
|
|
27503
|
+
truncatedByBudget: false
|
|
27504
|
+
});
|
|
27505
|
+
}
|
|
27266
27506
|
},
|
|
27267
27507
|
types: ["fact"],
|
|
27268
27508
|
limit: requestLimit,
|
|
@@ -27295,6 +27535,10 @@ function createMemoryVaultSearchTool(vaultCtx, embeddingOptions, cache, searchOp
|
|
|
27295
27535
|
|
|
27296
27536
|
${formatted}`;
|
|
27297
27537
|
} catch (error) {
|
|
27538
|
+
notifyMemoryCallback(
|
|
27539
|
+
callbacks?.onError,
|
|
27540
|
+
error instanceof Error ? error : new Error(String(error))
|
|
27541
|
+
);
|
|
27298
27542
|
const message = error instanceof Error ? error.message : "Unknown error";
|
|
27299
27543
|
return `Error searching vault: ${message}`;
|
|
27300
27544
|
}
|