memorix 1.4.6 → 1.5.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/CHANGELOG.md +38 -0
- package/TEAM.md +86 -86
- package/dist/cli/index.js +225 -70
- package/dist/cli/memcode.js +0 -0
- package/dist/index.js +225 -70
- package/dist/maintenance-runner.js +183 -38
- package/dist/media-audio-runner.js +183 -38
- package/dist/media-video-runner.js +183 -38
- package/dist/memcode-runtime/CHANGELOG.md +38 -0
- package/dist/sdk.js +224 -69
- package/dist/types.d.ts +2 -0
- package/dist/vector-backfill-runner.js +183 -38
- package/docs/CONFIGURATION.md +12 -0
- package/docs/DESIGN_DECISIONS.md +357 -357
- package/package.json +1 -1
- package/plugins/claude/memorix/.claude-plugin/plugin.json +1 -1
- package/plugins/codebuddy/memorix/.codebuddy-plugin/plugin.json +1 -1
- package/plugins/codex/memorix/.codex-plugin/plugin.json +1 -1
- package/plugins/copilot/memorix/plugin.json +1 -1
- package/plugins/gemini/memorix/gemini-extension.json +1 -1
- package/plugins/omp/memorix/package.json +1 -1
- package/plugins/openclaw/memorix/.codex-plugin/plugin.json +1 -1
- package/plugins/pi/memorix/package.json +1 -1
- package/server.json +2 -2
- package/src/audit/index.ts +156 -156
- package/src/cli/commands/formation.ts +48 -48
- package/src/cli/commands/git-hook-install.ts +111 -111
- package/src/cli/commands/handoff.ts +54 -54
- package/src/cli/commands/hooks-status.ts +63 -63
- package/src/cli/commands/ingest.ts +44 -44
- package/src/cli/commands/integrate-shared.ts +15 -15
- package/src/cli/commands/lock.ts +82 -82
- package/src/cli/commands/message.ts +104 -104
- package/src/cli/commands/poll.ts +58 -58
- package/src/cli/commands/reasoning.ts +118 -118
- package/src/cli/commands/skills.ts +114 -114
- package/src/cli/commands/task.ts +167 -167
- package/src/cli/commands/transfer.ts +47 -47
- package/src/cli/index.ts +406 -406
- package/src/cli/tui/ChatView.tsx +234 -234
- package/src/cli/tui/CommandBar.tsx +312 -312
- package/src/cli/tui/ContextRail.tsx +118 -118
- package/src/cli/tui/HeaderBar.tsx +72 -72
- package/src/cli/tui/LogoBanner.tsx +51 -51
- package/src/cli/tui/index.ts +41 -41
- package/src/cli/version.ts +7 -7
- package/src/cli/workbench.ts +1 -1
- package/src/config.ts +23 -2
- package/src/dashboard/project-classification.ts +64 -64
- package/src/embedding/api-provider.ts +105 -22
- package/src/embedding/provider.ts +2 -0
- package/src/git/hooks-path.ts +85 -85
- package/src/hooks/pattern-detector.ts +173 -173
- package/src/hooks/significance-filter.ts +250 -250
- package/src/llm/memory-manager.ts +328 -328
- package/src/llm/provider.ts +17 -8
- package/src/llm/quality.ts +248 -248
- package/src/memory/attribution-guard.ts +249 -249
- package/src/memory/disclosure-policy.ts +135 -135
- package/src/memory/entity-extractor.ts +197 -197
- package/src/memory/formation/evaluate.ts +217 -217
- package/src/memory/formation/extract.ts +6 -3
- package/src/memory/formation/index.ts +2 -1
- package/src/memory/formation/resolve.ts +10 -6
- package/src/memory/formation/types.ts +3 -1
- package/src/memory/freshness.ts +122 -122
- package/src/memory/graph.ts +197 -197
- package/src/memory/long-term.ts +7 -1
- package/src/memory/refs.ts +94 -94
- package/src/memory/secret-filter.ts +79 -79
- package/src/orchestrate/adapters/claude-stream.ts +192 -192
- package/src/orchestrate/adapters/claude.ts +111 -111
- package/src/orchestrate/adapters/codex-stream.ts +134 -134
- package/src/orchestrate/adapters/codex.ts +41 -41
- package/src/orchestrate/adapters/gemini-stream.ts +166 -166
- package/src/orchestrate/adapters/gemini.ts +42 -42
- package/src/orchestrate/adapters/index.ts +73 -73
- package/src/orchestrate/adapters/opencode-stream.ts +143 -143
- package/src/orchestrate/adapters/opencode.ts +47 -47
- package/src/orchestrate/adapters/types.ts +77 -77
- package/src/orchestrate/capability-router.ts +284 -284
- package/src/orchestrate/cost-tracker.ts +219 -219
- package/src/orchestrate/error-recovery.ts +191 -191
- package/src/orchestrate/evidence.ts +140 -140
- package/src/orchestrate/ledger.ts +110 -110
- package/src/orchestrate/memorix-bridge.ts +343 -343
- package/src/orchestrate/output-budget.ts +80 -80
- package/src/orchestrate/permission.ts +152 -152
- package/src/orchestrate/pipeline-trace.ts +131 -131
- package/src/orchestrate/prompt-builder.ts +155 -155
- package/src/orchestrate/ring-buffer.ts +37 -37
- package/src/orchestrate/task-graph.ts +389 -389
- package/src/project/aliases.ts +374 -374
- package/src/rules/adapters/trae.ts +56 -56
- package/src/rules/syncer.ts +235 -235
- package/src/search/query-expansion.ts +52 -52
- package/src/server/formation-timeout.ts +27 -27
- package/src/server.ts +14 -10
- package/src/skills/mini-skills.ts +386 -386
- package/src/store/chat-store.ts +119 -119
- package/src/store/graph-store.ts +249 -249
- package/src/store/mini-skill-store.ts +349 -349
- package/src/store/orama-store.ts +6 -4
- package/src/store/persistence-json.ts +212 -212
- package/src/store/persistence.ts +291 -291
- package/src/store/project-affinity.ts +195 -195
- package/src/team/event-bus.ts +76 -76
- package/src/team/handoff.ts +161 -161
- package/src/team/poll.ts +132 -132
- package/src/timeout.ts +67 -0
- package/src/types.ts +2 -0
- package/src/workspace/mcp-adapters/codex.ts +191 -191
- package/src/workspace/mcp-adapters/copilot.ts +105 -105
- package/src/workspace/mcp-adapters/cursor.ts +53 -53
- package/src/workspace/mcp-adapters/kiro.ts +64 -64
- package/src/workspace/mcp-adapters/opencode.ts +123 -123
- package/src/workspace/mcp-adapters/trae.ts +134 -134
- package/src/workspace/mcp-adapters/windsurf.ts +91 -91
- package/src/workspace/sanitizer.ts +60 -60
|
@@ -3124,6 +3124,7 @@ var init_resolved_config = __esm({
|
|
|
3124
3124
|
// src/config.ts
|
|
3125
3125
|
var config_exports = {};
|
|
3126
3126
|
__export(config_exports, {
|
|
3127
|
+
defaultEmbeddingModelFor: () => defaultEmbeddingModelFor,
|
|
3127
3128
|
getAgentLLMApiKey: () => getAgentLLMApiKey,
|
|
3128
3129
|
getAgentLLMBaseUrl: () => getAgentLLMBaseUrl,
|
|
3129
3130
|
getAgentLLMModel: () => getAgentLLMModel,
|
|
@@ -3186,7 +3187,19 @@ function getEmbeddingBaseUrl() {
|
|
|
3186
3187
|
return getResolvedEmbeddingLane().baseUrl || "https://api.openai.com/v1";
|
|
3187
3188
|
}
|
|
3188
3189
|
function getEmbeddingModel() {
|
|
3189
|
-
|
|
3190
|
+
const lane = getResolvedEmbeddingLane();
|
|
3191
|
+
return defaultEmbeddingModelFor(lane.baseUrl, lane.model);
|
|
3192
|
+
}
|
|
3193
|
+
function defaultEmbeddingModelFor(baseUrl, explicitModel) {
|
|
3194
|
+
if (explicitModel) return explicitModel;
|
|
3195
|
+
try {
|
|
3196
|
+
const url = baseUrl ? new URL(baseUrl) : null;
|
|
3197
|
+
if (url && (url.hostname === "openrouter.ai" || url.hostname.endsWith(".openrouter.ai"))) {
|
|
3198
|
+
return "qwen/qwen3-embedding-8b";
|
|
3199
|
+
}
|
|
3200
|
+
} catch {
|
|
3201
|
+
}
|
|
3202
|
+
return "text-embedding-3-small";
|
|
3190
3203
|
}
|
|
3191
3204
|
function getEmbeddingDimensions() {
|
|
3192
3205
|
return getResolvedEmbeddingLane().dimensions ?? null;
|
|
@@ -3725,6 +3738,8 @@ function getPreferredBatchSize(config) {
|
|
|
3725
3738
|
}
|
|
3726
3739
|
function parseBatchLimit(error) {
|
|
3727
3740
|
if (!(error instanceof Error)) return null;
|
|
3741
|
+
const status = error instanceof EmbeddingAPIError ? error.status : Number(error.message.match(/Embedding API error \((\d{3})\)/i)?.[1] ?? 0);
|
|
3742
|
+
if (status > 0 && status !== 400) return null;
|
|
3728
3743
|
const explicit = error.message.match(/should not be larger than\s+(\d+)/i);
|
|
3729
3744
|
if (explicit) return parseInt(explicit[1], 10);
|
|
3730
3745
|
if (/batch size/i.test(error.message)) {
|
|
@@ -3737,37 +3752,99 @@ async function fetchWithRetry(url, apiKey, body, options = {}, attempt = 0, nati
|
|
|
3737
3752
|
const controller = new AbortController();
|
|
3738
3753
|
const timeoutMs = typeof options.timeoutMs === "number" && Number.isFinite(options.timeoutMs) ? Math.max(100, Math.min(Math.floor(options.timeoutMs), 6e4)) : 1e4;
|
|
3739
3754
|
const timeout = setTimeout(() => controller.abort(), timeoutMs);
|
|
3755
|
+
const signal = options.signal ? AbortSignal.any([options.signal, controller.signal]) : controller.signal;
|
|
3740
3756
|
let response;
|
|
3741
3757
|
try {
|
|
3742
3758
|
response = await fetch(url, {
|
|
3743
3759
|
method: "POST",
|
|
3744
3760
|
headers: nativeGemini ? { "Content-Type": "application/json", "x-goog-api-key": apiKey } : { "Content-Type": "application/json", "Authorization": `Bearer ${apiKey}` },
|
|
3745
3761
|
body: JSON.stringify(body),
|
|
3746
|
-
signal
|
|
3762
|
+
signal
|
|
3747
3763
|
});
|
|
3748
3764
|
} catch (err) {
|
|
3749
3765
|
clearTimeout(timeout);
|
|
3750
|
-
if (err instanceof Error && err.name === "AbortError") {
|
|
3766
|
+
if (err instanceof Error && (err.name === "AbortError" || controller.signal.aborted || options.signal?.aborted)) {
|
|
3751
3767
|
throw new Error(`Embedding API timeout after ${timeoutMs}ms: ${url}`);
|
|
3752
3768
|
}
|
|
3753
3769
|
throw err;
|
|
3754
3770
|
}
|
|
3755
|
-
|
|
3756
|
-
|
|
3757
|
-
|
|
3771
|
+
try {
|
|
3772
|
+
if (response.ok) {
|
|
3773
|
+
return await raceWithAbort(
|
|
3774
|
+
response.json(),
|
|
3775
|
+
signal
|
|
3776
|
+
);
|
|
3777
|
+
}
|
|
3778
|
+
if (options.retry !== false && (response.status === 429 || response.status >= 500) && attempt < MAX_RETRIES2) {
|
|
3779
|
+
const delay2 = BASE_DELAY_MS * Math.pow(2, attempt);
|
|
3780
|
+
const retryAfter = response.headers.get("retry-after");
|
|
3781
|
+
const parsedRetryAfter = retryAfter ? parseInt(retryAfter, 10) * 1e3 : NaN;
|
|
3782
|
+
const waitMs = Number.isFinite(parsedRetryAfter) ? parsedRetryAfter : delay2;
|
|
3783
|
+
console.error(`[memorix] Embedding API ${response.status}, retry ${attempt + 1}/${MAX_RETRIES2} in ${waitMs}ms`);
|
|
3784
|
+
await waitForRetry(waitMs, options.signal);
|
|
3785
|
+
return fetchWithRetry(url, apiKey, body, options, attempt + 1, nativeGemini);
|
|
3786
|
+
}
|
|
3787
|
+
const errorText2 = await raceWithAbort(
|
|
3788
|
+
response.text().catch(() => "unknown error"),
|
|
3789
|
+
signal
|
|
3790
|
+
);
|
|
3791
|
+
throw new EmbeddingAPIError(response.status, errorText2);
|
|
3792
|
+
} catch (err) {
|
|
3793
|
+
if (err instanceof Error && (err.name === "AbortError" || controller.signal.aborted || options.signal?.aborted)) {
|
|
3794
|
+
throw new Error(`Embedding API timeout after ${timeoutMs}ms: ${url}`);
|
|
3795
|
+
}
|
|
3796
|
+
throw err;
|
|
3797
|
+
} finally {
|
|
3798
|
+
clearTimeout(timeout);
|
|
3758
3799
|
}
|
|
3759
|
-
|
|
3760
|
-
|
|
3761
|
-
|
|
3762
|
-
|
|
3763
|
-
|
|
3800
|
+
}
|
|
3801
|
+
function abortError() {
|
|
3802
|
+
const error = new Error("Embedding API request aborted");
|
|
3803
|
+
error.name = "AbortError";
|
|
3804
|
+
return error;
|
|
3805
|
+
}
|
|
3806
|
+
function raceWithAbort(promise, signal) {
|
|
3807
|
+
if (signal.aborted) return Promise.reject(abortError());
|
|
3808
|
+
return new Promise((resolve, reject) => {
|
|
3809
|
+
const onAbort = () => {
|
|
3810
|
+
signal.removeEventListener("abort", onAbort);
|
|
3811
|
+
reject(abortError());
|
|
3812
|
+
};
|
|
3813
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
3814
|
+
promise.then(
|
|
3815
|
+
(value) => {
|
|
3816
|
+
signal.removeEventListener("abort", onAbort);
|
|
3817
|
+
resolve(value);
|
|
3818
|
+
},
|
|
3819
|
+
(error) => {
|
|
3820
|
+
signal.removeEventListener("abort", onAbort);
|
|
3821
|
+
reject(error);
|
|
3822
|
+
}
|
|
3823
|
+
);
|
|
3824
|
+
});
|
|
3825
|
+
}
|
|
3826
|
+
async function waitForRetry(waitMs, signal) {
|
|
3827
|
+
if (!signal) {
|
|
3764
3828
|
await new Promise((resolve) => setTimeout(resolve, waitMs));
|
|
3765
|
-
return
|
|
3829
|
+
return;
|
|
3766
3830
|
}
|
|
3767
|
-
const
|
|
3768
|
-
throw new Error(
|
|
3831
|
+
const abortSignal = signal;
|
|
3832
|
+
if (abortSignal.aborted) throw new Error("Embedding API retry aborted");
|
|
3833
|
+
await new Promise((resolve, reject) => {
|
|
3834
|
+
const timer = setTimeout(done, waitMs);
|
|
3835
|
+
const onAbort = () => {
|
|
3836
|
+
clearTimeout(timer);
|
|
3837
|
+
abortSignal.removeEventListener("abort", onAbort);
|
|
3838
|
+
reject(new Error("Embedding API retry aborted"));
|
|
3839
|
+
};
|
|
3840
|
+
function done() {
|
|
3841
|
+
abortSignal.removeEventListener("abort", onAbort);
|
|
3842
|
+
resolve();
|
|
3843
|
+
}
|
|
3844
|
+
abortSignal.addEventListener("abort", onAbort, { once: true });
|
|
3845
|
+
});
|
|
3769
3846
|
}
|
|
3770
|
-
var cache3, MAX_CACHE_SIZE3, diskCacheDirty2, diskSaveTimer, diskCacheLoaded, diskCacheLoadPromise, MAX_INPUT_CHARS, MAX_CONCURRENCY, DISK_SAVE_DEBOUNCE_MS, DEFAULT_MAX_BATCH_SIZE, DASHSCOPE_MAX_BATCH_SIZE, MAX_RETRIES2, BASE_DELAY_MS, APIEmbeddingProvider;
|
|
3847
|
+
var cache3, MAX_CACHE_SIZE3, diskCacheDirty2, diskSaveTimer, diskCacheLoaded, diskCacheLoadPromise, MAX_INPUT_CHARS, MAX_CONCURRENCY, DISK_SAVE_DEBOUNCE_MS, DEFAULT_MAX_BATCH_SIZE, DASHSCOPE_MAX_BATCH_SIZE, MAX_RETRIES2, BASE_DELAY_MS, EmbeddingAPIError, APIEmbeddingProvider;
|
|
3771
3848
|
var init_api_provider = __esm({
|
|
3772
3849
|
"src/embedding/api-provider.ts"() {
|
|
3773
3850
|
"use strict";
|
|
@@ -3786,6 +3863,14 @@ var init_api_provider = __esm({
|
|
|
3786
3863
|
DASHSCOPE_MAX_BATCH_SIZE = 10;
|
|
3787
3864
|
MAX_RETRIES2 = 3;
|
|
3788
3865
|
BASE_DELAY_MS = 500;
|
|
3866
|
+
EmbeddingAPIError = class extends Error {
|
|
3867
|
+
status;
|
|
3868
|
+
constructor(status, detail) {
|
|
3869
|
+
super(`Embedding API error (${status}): ${detail}`);
|
|
3870
|
+
this.name = "EmbeddingAPIError";
|
|
3871
|
+
this.status = status;
|
|
3872
|
+
}
|
|
3873
|
+
};
|
|
3789
3874
|
APIEmbeddingProvider = class _APIEmbeddingProvider {
|
|
3790
3875
|
name;
|
|
3791
3876
|
dimensions;
|
|
@@ -3997,15 +4082,14 @@ var init_api_provider = __esm({
|
|
|
3997
4082
|
}
|
|
3998
4083
|
} catch (error) {
|
|
3999
4084
|
const providerLimit = parseBatchLimit(error);
|
|
4000
|
-
|
|
4001
|
-
if (chunkTexts.length > 1 && fallbackSize < chunkTexts.length) {
|
|
4085
|
+
if (providerLimit !== null && chunkTexts.length > 1 && providerLimit < chunkTexts.length) {
|
|
4002
4086
|
console.error(
|
|
4003
|
-
`[memorix] Embedding batch too large for provider, retrying in chunks of ${
|
|
4087
|
+
`[memorix] Embedding batch too large for provider, retrying in chunks of ${providerLimit}`
|
|
4004
4088
|
);
|
|
4005
|
-
for (let start = 0; start < chunkTexts.length; start +=
|
|
4089
|
+
for (let start = 0; start < chunkTexts.length; start += providerLimit) {
|
|
4006
4090
|
await processChunk(
|
|
4007
|
-
chunkTexts.slice(start, start +
|
|
4008
|
-
chunkIndices.slice(start, start +
|
|
4091
|
+
chunkTexts.slice(start, start + providerLimit),
|
|
4092
|
+
chunkIndices.slice(start, start + providerLimit)
|
|
4009
4093
|
);
|
|
4010
4094
|
}
|
|
4011
4095
|
return;
|
|
@@ -4869,22 +4953,23 @@ function getLLMConfig() {
|
|
|
4869
4953
|
function setLLMConfig(config) {
|
|
4870
4954
|
currentConfig = config;
|
|
4871
4955
|
}
|
|
4872
|
-
async function callLLM(systemPrompt, userMessage) {
|
|
4956
|
+
async function callLLM(systemPrompt, userMessage, signal) {
|
|
4873
4957
|
if (!currentConfig) {
|
|
4874
4958
|
throw new Error("LLM not configured. Set MEMORIX_LLM_API_KEY or OPENAI_API_KEY.");
|
|
4875
4959
|
}
|
|
4876
4960
|
if (currentConfig.provider === "anthropic") {
|
|
4877
|
-
return callAnthropic(systemPrompt, userMessage);
|
|
4961
|
+
return callAnthropic(systemPrompt, userMessage, signal);
|
|
4878
4962
|
}
|
|
4879
|
-
return callOpenAICompatible(systemPrompt, userMessage);
|
|
4963
|
+
return callOpenAICompatible(systemPrompt, userMessage, signal);
|
|
4880
4964
|
}
|
|
4881
|
-
async function callOpenAICompatible(systemPrompt, userMessage) {
|
|
4965
|
+
async function callOpenAICompatible(systemPrompt, userMessage, signal) {
|
|
4882
4966
|
const config = currentConfig;
|
|
4883
4967
|
let base = config.baseUrl.replace(/\/+$/, "");
|
|
4884
4968
|
if (!base.endsWith("/v1")) base += "/v1";
|
|
4885
4969
|
const url = `${base}/chat/completions`;
|
|
4970
|
+
const fetchSignal = signal ? AbortSignal.any([signal, AbortSignal.timeout(LLM_CALL_TIMEOUT_MS)]) : AbortSignal.timeout(LLM_CALL_TIMEOUT_MS);
|
|
4886
4971
|
const response = await fetch(url, {
|
|
4887
|
-
signal:
|
|
4972
|
+
signal: fetchSignal,
|
|
4888
4973
|
method: "POST",
|
|
4889
4974
|
headers: {
|
|
4890
4975
|
"Content-Type": "application/json",
|
|
@@ -4901,10 +4986,10 @@ async function callOpenAICompatible(systemPrompt, userMessage) {
|
|
|
4901
4986
|
})
|
|
4902
4987
|
});
|
|
4903
4988
|
if (!response.ok) {
|
|
4904
|
-
const error = await readResponseText(response,
|
|
4989
|
+
const error = await readResponseText(response, signal, 64 * 1024).catch(() => "unknown error");
|
|
4905
4990
|
throw new Error(`LLM API error (${response.status}): ${error}`);
|
|
4906
4991
|
}
|
|
4907
|
-
const data = await readResponseJson(response);
|
|
4992
|
+
const data = await readResponseJson(response, signal);
|
|
4908
4993
|
return {
|
|
4909
4994
|
content: data.choices[0]?.message?.content ?? "",
|
|
4910
4995
|
usage: data.usage ? {
|
|
@@ -4913,11 +4998,12 @@ async function callOpenAICompatible(systemPrompt, userMessage) {
|
|
|
4913
4998
|
} : void 0
|
|
4914
4999
|
};
|
|
4915
5000
|
}
|
|
4916
|
-
async function callAnthropic(systemPrompt, userMessage) {
|
|
5001
|
+
async function callAnthropic(systemPrompt, userMessage, signal) {
|
|
4917
5002
|
const config = currentConfig;
|
|
4918
5003
|
const url = `${config.baseUrl}/messages`;
|
|
5004
|
+
const fetchSignal = signal ? AbortSignal.any([signal, AbortSignal.timeout(LLM_CALL_TIMEOUT_MS)]) : AbortSignal.timeout(LLM_CALL_TIMEOUT_MS);
|
|
4919
5005
|
const response = await fetch(url, {
|
|
4920
|
-
signal:
|
|
5006
|
+
signal: fetchSignal,
|
|
4921
5007
|
method: "POST",
|
|
4922
5008
|
headers: {
|
|
4923
5009
|
"Content-Type": "application/json",
|
|
@@ -4935,10 +5021,10 @@ async function callAnthropic(systemPrompt, userMessage) {
|
|
|
4935
5021
|
})
|
|
4936
5022
|
});
|
|
4937
5023
|
if (!response.ok) {
|
|
4938
|
-
const error = await readResponseText(response,
|
|
5024
|
+
const error = await readResponseText(response, signal, 64 * 1024).catch(() => "unknown error");
|
|
4939
5025
|
throw new Error(`Anthropic API error (${response.status}): ${error}`);
|
|
4940
5026
|
}
|
|
4941
|
-
const data = await readResponseJson(response);
|
|
5027
|
+
const data = await readResponseJson(response, signal);
|
|
4942
5028
|
return {
|
|
4943
5029
|
content: data.content[0]?.text ?? "",
|
|
4944
5030
|
usage: data.usage ? {
|
|
@@ -5443,6 +5529,57 @@ function withTimeout(promise, ms, label) {
|
|
|
5443
5529
|
);
|
|
5444
5530
|
});
|
|
5445
5531
|
}
|
|
5532
|
+
function withTimeoutSignal(operation, ms, label, parentSignal) {
|
|
5533
|
+
const controller = new AbortController();
|
|
5534
|
+
const signal = parentSignal ? AbortSignal.any([parentSignal, controller.signal]) : controller.signal;
|
|
5535
|
+
return new Promise((resolve, reject) => {
|
|
5536
|
+
let settled = false;
|
|
5537
|
+
let timedOut = false;
|
|
5538
|
+
let timer;
|
|
5539
|
+
const cleanup = () => {
|
|
5540
|
+
if (timer !== void 0) clearTimeout(timer);
|
|
5541
|
+
parentSignal?.removeEventListener("abort", onParentAbort);
|
|
5542
|
+
};
|
|
5543
|
+
const onParentAbort = () => {
|
|
5544
|
+
if (settled || timedOut) return;
|
|
5545
|
+
settled = true;
|
|
5546
|
+
cleanup();
|
|
5547
|
+
reject(parentSignal?.reason ?? new Error(`${label} aborted`));
|
|
5548
|
+
};
|
|
5549
|
+
parentSignal?.addEventListener("abort", onParentAbort, { once: true });
|
|
5550
|
+
timer = setTimeout(() => {
|
|
5551
|
+
if (settled) return;
|
|
5552
|
+
timedOut = true;
|
|
5553
|
+
controller.abort(new Error(`${label} timed out after ${ms}ms`));
|
|
5554
|
+
settled = true;
|
|
5555
|
+
cleanup();
|
|
5556
|
+
reject(new Error(`${label} timed out after ${ms}ms`));
|
|
5557
|
+
}, ms);
|
|
5558
|
+
let pending;
|
|
5559
|
+
try {
|
|
5560
|
+
pending = operation(signal);
|
|
5561
|
+
} catch (error) {
|
|
5562
|
+
settled = true;
|
|
5563
|
+
cleanup();
|
|
5564
|
+
reject(error);
|
|
5565
|
+
return;
|
|
5566
|
+
}
|
|
5567
|
+
pending.then(
|
|
5568
|
+
(value) => {
|
|
5569
|
+
if (settled) return;
|
|
5570
|
+
settled = true;
|
|
5571
|
+
cleanup();
|
|
5572
|
+
resolve(value);
|
|
5573
|
+
},
|
|
5574
|
+
(error) => {
|
|
5575
|
+
if (settled) return;
|
|
5576
|
+
settled = true;
|
|
5577
|
+
cleanup();
|
|
5578
|
+
reject(timedOut ? new Error(`${label} timed out after ${ms}ms`) : error);
|
|
5579
|
+
}
|
|
5580
|
+
);
|
|
5581
|
+
});
|
|
5582
|
+
}
|
|
5446
5583
|
var init_timeout = __esm({
|
|
5447
5584
|
"src/timeout.ts"() {
|
|
5448
5585
|
"use strict";
|
|
@@ -6307,16 +6444,18 @@ async function searchObservations(options) {
|
|
|
6307
6444
|
);
|
|
6308
6445
|
} else {
|
|
6309
6446
|
const EMBEDDING_TIMEOUT_MS = 15e3;
|
|
6310
|
-
queryVector = await
|
|
6311
|
-
provider2.embedInput ? provider2.embedInput(
|
|
6447
|
+
queryVector = await withTimeoutSignal(
|
|
6448
|
+
(signal) => provider2.embedInput ? provider2.embedInput(
|
|
6312
6449
|
{ modality: "text", text: expandedEmbeddingQuery },
|
|
6313
|
-
{ intent: "query", timeoutMs: EMBEDDING_TIMEOUT_MS, retry: false }
|
|
6450
|
+
{ intent: "query", timeoutMs: EMBEDDING_TIMEOUT_MS, retry: false, signal }
|
|
6314
6451
|
) : provider2.embed(expandedEmbeddingQuery, {
|
|
6315
6452
|
timeoutMs: EMBEDDING_TIMEOUT_MS,
|
|
6316
|
-
retry: false
|
|
6453
|
+
retry: false,
|
|
6454
|
+
signal
|
|
6317
6455
|
}),
|
|
6318
6456
|
EMBEDDING_TIMEOUT_MS,
|
|
6319
|
-
"Embedding"
|
|
6457
|
+
"Embedding",
|
|
6458
|
+
options.signal
|
|
6320
6459
|
);
|
|
6321
6460
|
mark("embedding");
|
|
6322
6461
|
const cjkRatio = (originalQuery.match(/[\u4e00-\u9fff\u3040-\u309f\u30a0-\u30ff\uac00-\ud7af]/g) || []).length / originalQuery.length;
|
|
@@ -142914,7 +143053,13 @@ async function maintainLongTermMemories(input) {
|
|
|
142914
143053
|
}
|
|
142915
143054
|
for (const group of groups.values()) {
|
|
142916
143055
|
if (group.length < 2) continue;
|
|
142917
|
-
group.sort((a, b) =>
|
|
143056
|
+
group.sort((a, b) => {
|
|
143057
|
+
const byCreatedAt = Date.parse(b.createdAt) - Date.parse(a.createdAt);
|
|
143058
|
+
if (byCreatedAt !== 0) return byCreatedAt;
|
|
143059
|
+
const byUpdatedAt = Date.parse(b.updatedAt) - Date.parse(a.updatedAt);
|
|
143060
|
+
if (byUpdatedAt !== 0) return byUpdatedAt;
|
|
143061
|
+
return b.id.localeCompare(a.id);
|
|
143062
|
+
});
|
|
142918
143063
|
const newest = group[0];
|
|
142919
143064
|
for (const older of group.slice(1)) {
|
|
142920
143065
|
try {
|