switchroom 0.19.23 → 0.19.24
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/agent-scheduler/index.js +4 -2
- package/dist/auth-broker/index.js +35 -9
- package/dist/cli/notion-write-pretool.mjs +4 -2
- package/dist/cli/switchroom.js +242 -82
- package/dist/host-control/main.js +36 -10
- package/dist/vault/approvals/kernel-server.js +35 -9
- package/dist/vault/broker/server.js +35 -9
- package/package.json +1 -1
- package/profiles/_shared/dev-protocol.md.hbs +3 -4
- package/skills/dev-protocol/SKILL.md +22 -15
- package/skills/switchroom-release/SKILL.md +2 -1
- package/telegram-plugin/dist/gateway/gateway.js +171 -48
- package/telegram-plugin/gateway/gateway.ts +34 -35
- package/telegram-plugin/gateway/latest-turn-lookup.ts +60 -0
- package/telegram-plugin/gateway/outbound-send-path.ts +53 -21
- package/telegram-plugin/gateway/subagent-handback-marker.ts +1 -1
- package/telegram-plugin/gateway/turn-end.ts +1 -1
- package/telegram-plugin/reply-owner-resolve.ts +110 -9
- package/telegram-plugin/send-gate-degraded.test.ts +45 -16
- package/telegram-plugin/send-gate.ts +185 -24
- package/telegram-plugin/tests/activity-card-send-gate.test.ts +9 -9
- package/telegram-plugin/tests/latest-turn-lookup.test.ts +77 -0
- package/telegram-plugin/tests/narrative-lane-golden.test.ts +23 -1
- package/telegram-plugin/tests/reply-owner-resolve.test.ts +531 -0
- package/telegram-plugin/tests/send-reply-golden.test.ts +296 -28
- package/telegram-plugin/tests/stream-controller-send-gate.test.ts +134 -28
- package/telegram-plugin/tests/stream-render-golden.test.ts +25 -3
package/dist/cli/switchroom.js
CHANGED
|
@@ -2120,7 +2120,7 @@ var init_esm = __esm(() => {
|
|
|
2120
2120
|
});
|
|
2121
2121
|
|
|
2122
2122
|
// src/build-info.ts
|
|
2123
|
-
var VERSION = "0.19.
|
|
2123
|
+
var VERSION = "0.19.24", COMMIT_SHA = "0fa8ffb8";
|
|
2124
2124
|
|
|
2125
2125
|
// src/cli/resolve-version.ts
|
|
2126
2126
|
import { existsSync, readFileSync } from "node:fs";
|
|
@@ -13939,17 +13939,19 @@ var init_schema = __esm(() => {
|
|
|
13939
13939
|
model: exports_external.string().min(1).optional().describe("Per-op model (upstream `HINDSIGHT_API_<OP>_LLM_MODEL`). Absent \u2192 " + "inherit the global `hindsight.llm.model`."),
|
|
13940
13940
|
provider: exports_external.string().min(1).optional().describe("Per-op provider (upstream `HINDSIGHT_API_<OP>_LLM_PROVIDER`). " + "Absent \u2192 inherit the global `hindsight.llm.provider`."),
|
|
13941
13941
|
base_url: exports_external.string().min(1).optional().describe("Per-op base URL (upstream `HINDSIGHT_API_<OP>_LLM_BASE_URL`). " + "Optional passthrough; absent \u2192 inherit the global."),
|
|
13942
|
-
api_key: exports_external.string().min(1).optional().describe("Per-op API key (upstream `HINDSIGHT_API_<OP>_LLM_API_KEY`). Literal " + "or `vault:` reference. Optional passthrough; absent \u2192 inherit global.")
|
|
13942
|
+
api_key: exports_external.string().min(1).optional().describe("Per-op API key (upstream `HINDSIGHT_API_<OP>_LLM_API_KEY`). Literal " + "or `vault:` reference. Optional passthrough; absent \u2192 inherit global."),
|
|
13943
|
+
context_window: exports_external.number().int().positive().optional().describe("Context window (tokens) of the backend serving THIS op. NOT an " + "upstream env var \u2014 switchroom derives the op's token budget " + "(consolidation batch size / max-completion caps / reflect " + "max-context cap) from it so a single call can never overflow the " + "window. Absent \u2192 inherit " + "`hindsight.llm.context_window`, else a per-provider default " + "(conservative for non-`claude-code` providers, which usually mean " + "a local llama.cpp/Ollama slot; a self-hosted `base_url` \u2014 loopback, " + "RFC1918, `.local`/`.internal` \u2014 forces the conservative default too, " + "regardless of the provider NAME, since the endpoint is where the " + "traffic actually terminates). All three lanes (`retain`, " + "`reflect`, `consolidation`) are budgeted independently.")
|
|
13943
13944
|
}).describe("Per-operation LLM override. Every field optional; an unset field (or " + "an omitted op block) inherits the global `hindsight.llm.*`, which is " + "already the engine's fallback \u2014 switchroom emits only the vars set.");
|
|
13944
13945
|
HindsightConfigSchema = exports_external.object({
|
|
13945
13946
|
llm: exports_external.object({
|
|
13946
13947
|
provider: exports_external.string().min(1).optional().describe("Hindsight LLM provider (upstream `HINDSIGHT_API_LLM_PROVIDER`). " + "Defaults to `claude-code` (subscription-honest, broker-fed OAuth). " + "Any litellm-routable provider the upstream image supports is valid. " + "Serves as the GLOBAL default for every op absent a per-op override."),
|
|
13947
13948
|
model: exports_external.string().min(1).optional().describe("Hindsight LLM model (upstream `HINDSIGHT_API_LLM_MODEL`). Defaults " + "to HINDSIGHT_DEFAULT_MODEL. Any model your LiteLLM proxy can route " + "is valid, e.g. `openrouter/z-ai/glm-5.2` when routing through the " + "fleet proxy. With provider=claude-code this value is ALSO exported " + "as `ANTHROPIC_MODEL` to the claude subprocess. Serves as the GLOBAL " + "default for every op absent a per-op override."),
|
|
13949
|
+
context_window: exports_external.number().int().positive().optional().describe("GLOBAL context window (tokens) of the backend serving hindsight's " + "LLM ops \u2014 the declared size switchroom derives every token budget " + "from. Set this to the real window of whatever you point " + "`hindsight.llm` at (e.g. 32768 for a llama.cpp slot launched with " + "`-c 65536 -np 2`, 131072 for a large-window OpenRouter model). " + "Absent \u2192 a per-provider default: 200000 for `claude-code`, a " + "conservative 32768 for everything else. Overflowing a local " + "backend's window does NOT error \u2014 llama.cpp context-shift silently " + "drops the system prompt and the model answers conversationally " + "with HTTP 200 \u2014 so this value is what makes the failure " + "detectable at setup time instead of never."),
|
|
13948
13950
|
retain: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `retain` LLM op (memory ingestion). Emits " + "`HINDSIGHT_API_RETAIN_LLM_*`. Absent \u2192 uses the global model/provider."),
|
|
13949
13951
|
reflect: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `reflect` LLM op (synthesis / mental-model " + "refresh). Emits `HINDSIGHT_API_REFLECT_LLM_*`. Absent \u2192 uses global."),
|
|
13950
13952
|
consolidation: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `consolidation` LLM op (background memory " + "merge). Emits `HINDSIGHT_API_CONSOLIDATION_LLM_*`. Absent \u2192 global.")
|
|
13951
13953
|
}).optional().describe("LLM knob for the hindsight container. The flat `provider`/`model` set " + "the global default (backward-compatible); optional `retain`/`reflect`/" + "`consolidation` blocks override individual ops. All fields optional; " + "unset fields fall back to the hard-coded defaults."),
|
|
13952
|
-
env: exports_external.record(exports_external.union([exports_external.string(), exports_external.number(), exports_external.boolean()])).optional().describe("Operator overrides for switchroom's capability-gated Hindsight " + "performance defaults. Only the keys switchroom actually manages are " + "honoured (`HINDSIGHT_PERF_ENV_KEYS` in " + "src/setup/hindsight-perf-defaults.ts: RERANKER_LOCAL_FP16, " + "LLM_MAX_CONCURRENT, RETAIN/CONSOLIDATION_LLM_MAX_CONCURRENT, " + "RECALL_MAX_CANDIDATES_PER_SOURCE, LINK_EXPANSION_PER_ENTITY_LIMIT, " + "LINK_EXPANSION_TIMEOUT, LLM_REASONING_EFFORT), plus the " + "embedded-PostgreSQL (pg0) sizing keys switchroom manages in " + "src/setup/hindsight-pg-defaults.ts (`HINDSIGHT_PG_ENV_KEYS`: " + "SWITCHROOM_HINDSIGHT_PG_EFFECTIVE_CACHE_SIZE, " + "SWITCHROOM_HINDSIGHT_PG_SHARED_BUFFERS \u2014 a postgres size string such " + "as `4GB`, or the sentinel `off` to leave pg0's own default for that " + "one knob). A value set here " + "REPLACES switchroom's default and is emitted even when the gating " + "capability is absent, so an operator can always force a knob. Other " + "`HINDSIGHT_API_*` keys are deliberately IGNORED \u2014 a blanket " + "passthrough would collide with the vars startHindsight() derives " + "itself (HINDSIGHT_API_PORT, the retain token/deadline budget).")
|
|
13954
|
+
env: exports_external.record(exports_external.union([exports_external.string(), exports_external.number(), exports_external.boolean()])).optional().describe("Operator overrides for switchroom's capability-gated Hindsight " + "performance defaults. Only the keys switchroom actually manages are " + "honoured (`HINDSIGHT_PERF_ENV_KEYS` in " + "src/setup/hindsight-perf-defaults.ts: RERANKER_LOCAL_FP16, " + "RERANKER_LOCAL_BATCH_SIZE, LLM_MAX_CONCURRENT, " + "RETAIN/CONSOLIDATION_LLM_MAX_CONCURRENT, LLM_STRICT_SCHEMA, " + "LLM_MAX_RETRIES, CONSOLIDATION_LLM_PARALLELISM, " + "RECALL_MAX_CANDIDATES_PER_SOURCE, LINK_EXPANSION_PER_ENTITY_LIMIT, " + "LINK_EXPANSION_TIMEOUT, LLM_REASONING_EFFORT), the override-only keys " + "switchroom manages but ships NO default for " + "(`HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS`: " + "HINDSIGHT_API_WORKER_CONSOLIDATION_BANK_PRIORITY \u2014 a per-deployment " + "`bank-pattern:priority,...` map; unset means upstream's flat " + "created_at FIFO across banks), plus the " + "embedded-PostgreSQL (pg0) sizing keys switchroom manages in " + "src/setup/hindsight-pg-defaults.ts (`HINDSIGHT_PG_ENV_KEYS`: " + "SWITCHROOM_HINDSIGHT_PG_EFFECTIVE_CACHE_SIZE, " + "SWITCHROOM_HINDSIGHT_PG_SHARED_BUFFERS \u2014 a postgres size string such " + "as `4GB`, or the sentinel `off` to leave pg0's own default for that " + "one knob). A value set here " + "REPLACES switchroom's default and is emitted even when the gating " + "capability is absent, so an operator can always force a knob. Other " + "`HINDSIGHT_API_*` keys are deliberately IGNORED \u2014 a blanket " + "passthrough would collide with the vars startHindsight() derives " + "itself (HINDSIGHT_API_PORT, the retain token/deadline budget).")
|
|
13953
13955
|
});
|
|
13954
13956
|
MicrosoftWorkspaceConfigSchema = exports_external.object({
|
|
13955
13957
|
microsoft_client_id: exports_external.string().min(1).optional().describe("Microsoft OAuth application (client) ID from Entra portal " + "(literal string or vault reference e.g. " + "'vault:microsoft-oauth-client-id'). OPTIONAL \u2014 omit it to use " + "switchroom's shipped default Microsoft app (zero-config). " + "Set it only to bring your own Entra app (BYO)."),
|
|
@@ -15645,7 +15647,7 @@ function hindsightPerfEnv(caps, overrides = new Map) {
|
|
|
15645
15647
|
}
|
|
15646
15648
|
return out;
|
|
15647
15649
|
}
|
|
15648
|
-
var HINDSIGHT_RERANKER_MAX_CANDIDATES_FOR_DERIVATION = 150, HINDSIGHT_DEFAULT_RECALL_MAX_CANDIDATES_PER_SOURCE, HINDSIGHT_DEFAULT_LINK_EXPANSION_PER_ENTITY_LIMIT = 50, HINDSIGHT_DEFAULT_LINK_EXPANSION_TIMEOUT_S = 2, HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT = "low", HINDSIGHT_DEFAULT_LLM_MAX_CONCURRENT = 4, HINDSIGHT_DEFAULT_RETAIN_LLM_MAX_CONCURRENT = 1, HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_MAX_CONCURRENT = 1, HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16 = "true", HINDSIGHT_PERF_DEFAULTS_UNGATED, HINDSIGHT_PERF_DEFAULTS_GPU, HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM, HINDSIGHT_PERF_ENV_KEYS;
|
|
15650
|
+
var HINDSIGHT_RERANKER_MAX_CANDIDATES_FOR_DERIVATION = 150, HINDSIGHT_DEFAULT_RECALL_MAX_CANDIDATES_PER_SOURCE, HINDSIGHT_DEFAULT_LINK_EXPANSION_PER_ENTITY_LIMIT = 50, HINDSIGHT_DEFAULT_LINK_EXPANSION_TIMEOUT_S = 2, HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT = "low", HINDSIGHT_DEFAULT_LLM_MAX_CONCURRENT = 4, HINDSIGHT_DEFAULT_RETAIN_LLM_MAX_CONCURRENT = 1, HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_MAX_CONCURRENT = 1, HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16 = "true", HINDSIGHT_DEFAULT_RERANKER_LOCAL_BATCH_SIZE = 128, HINDSIGHT_DEFAULT_LLM_STRICT_SCHEMA = "true", HINDSIGHT_DEFAULT_LLM_MAX_RETRIES = 2, HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_PARALLELISM = 2, HINDSIGHT_PERF_DEFAULTS_UNGATED, HINDSIGHT_PERF_DEFAULTS_GPU, HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM, HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS, HINDSIGHT_PERF_ENV_KEYS;
|
|
15649
15651
|
var init_hindsight_perf_defaults = __esm(() => {
|
|
15650
15652
|
HINDSIGHT_DEFAULT_RECALL_MAX_CANDIDATES_PER_SOURCE = Math.ceil(HINDSIGHT_RERANKER_MAX_CANDIDATES_FOR_DERIVATION * 0.4);
|
|
15651
15653
|
HINDSIGHT_PERF_DEFAULTS_UNGATED = [
|
|
@@ -15661,10 +15663,18 @@ var init_hindsight_perf_defaults = __esm(() => {
|
|
|
15661
15663
|
"HINDSIGHT_API_LINK_EXPANSION_TIMEOUT",
|
|
15662
15664
|
String(HINDSIGHT_DEFAULT_LINK_EXPANSION_TIMEOUT_S)
|
|
15663
15665
|
],
|
|
15664
|
-
["HINDSIGHT_API_LLM_REASONING_EFFORT", HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT]
|
|
15666
|
+
["HINDSIGHT_API_LLM_REASONING_EFFORT", HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT],
|
|
15667
|
+
[
|
|
15668
|
+
"HINDSIGHT_API_CONSOLIDATION_LLM_PARALLELISM",
|
|
15669
|
+
String(HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_PARALLELISM)
|
|
15670
|
+
]
|
|
15665
15671
|
];
|
|
15666
15672
|
HINDSIGHT_PERF_DEFAULTS_GPU = [
|
|
15667
|
-
["HINDSIGHT_API_RERANKER_LOCAL_FP16", HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16]
|
|
15673
|
+
["HINDSIGHT_API_RERANKER_LOCAL_FP16", HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16],
|
|
15674
|
+
[
|
|
15675
|
+
"HINDSIGHT_API_RERANKER_LOCAL_BATCH_SIZE",
|
|
15676
|
+
String(HINDSIGHT_DEFAULT_RERANKER_LOCAL_BATCH_SIZE)
|
|
15677
|
+
]
|
|
15668
15678
|
];
|
|
15669
15679
|
HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM = [
|
|
15670
15680
|
["HINDSIGHT_API_LLM_MAX_CONCURRENT", String(HINDSIGHT_DEFAULT_LLM_MAX_CONCURRENT)],
|
|
@@ -15675,13 +15685,21 @@ var init_hindsight_perf_defaults = __esm(() => {
|
|
|
15675
15685
|
[
|
|
15676
15686
|
"HINDSIGHT_API_CONSOLIDATION_LLM_MAX_CONCURRENT",
|
|
15677
15687
|
String(HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_MAX_CONCURRENT)
|
|
15678
|
-
]
|
|
15688
|
+
],
|
|
15689
|
+
["HINDSIGHT_API_LLM_STRICT_SCHEMA", HINDSIGHT_DEFAULT_LLM_STRICT_SCHEMA],
|
|
15690
|
+
["HINDSIGHT_API_LLM_MAX_RETRIES", String(HINDSIGHT_DEFAULT_LLM_MAX_RETRIES)]
|
|
15679
15691
|
];
|
|
15692
|
+
HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS = new Set([
|
|
15693
|
+
"HINDSIGHT_API_WORKER_CONSOLIDATION_BANK_PRIORITY"
|
|
15694
|
+
]);
|
|
15680
15695
|
HINDSIGHT_PERF_ENV_KEYS = new Set([
|
|
15681
|
-
...
|
|
15682
|
-
|
|
15683
|
-
|
|
15684
|
-
|
|
15696
|
+
...[
|
|
15697
|
+
...HINDSIGHT_PERF_DEFAULTS_UNGATED,
|
|
15698
|
+
...HINDSIGHT_PERF_DEFAULTS_GPU,
|
|
15699
|
+
...HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM
|
|
15700
|
+
].map(([k]) => k),
|
|
15701
|
+
...HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS
|
|
15702
|
+
]);
|
|
15685
15703
|
});
|
|
15686
15704
|
|
|
15687
15705
|
// src/setup/hindsight-pg-defaults.ts
|
|
@@ -15731,6 +15749,185 @@ var init_hindsight_pg_defaults = __esm(() => {
|
|
|
15731
15749
|
HINDSIGHT_PG_ENV_KEYS = new Set(HINDSIGHT_PG_DEFAULTS.map(([k]) => k));
|
|
15732
15750
|
});
|
|
15733
15751
|
|
|
15752
|
+
// src/setup/self-hosted-url.ts
|
|
15753
|
+
function isLoopbackHttpUrl(url) {
|
|
15754
|
+
try {
|
|
15755
|
+
const u = new URL(url.includes("://") ? url : `http://${url}`);
|
|
15756
|
+
const h = (u.hostname || "").toLowerCase().replace(/^\[|\]$/g, "");
|
|
15757
|
+
return h === "localhost" || h === "127.0.0.1" || h === "::1";
|
|
15758
|
+
} catch {
|
|
15759
|
+
return false;
|
|
15760
|
+
}
|
|
15761
|
+
}
|
|
15762
|
+
function isSelfHostedHttpUrl(url) {
|
|
15763
|
+
let host;
|
|
15764
|
+
try {
|
|
15765
|
+
const u = new URL(url.includes("://") ? url : `http://${url}`);
|
|
15766
|
+
host = (u.hostname || "").toLowerCase().replace(/^\[|\]$/g, "");
|
|
15767
|
+
} catch {
|
|
15768
|
+
return false;
|
|
15769
|
+
}
|
|
15770
|
+
if (!host)
|
|
15771
|
+
return false;
|
|
15772
|
+
if (isLoopbackHttpUrl(url))
|
|
15773
|
+
return true;
|
|
15774
|
+
if (host === "host.docker.internal" || host === "gateway.docker.internal")
|
|
15775
|
+
return true;
|
|
15776
|
+
if (host.endsWith(".local") || host.endsWith(".internal"))
|
|
15777
|
+
return true;
|
|
15778
|
+
if (/^f[cd][0-9a-f]{2}:/.test(host) || /^fe[89ab][0-9a-f]:/.test(host))
|
|
15779
|
+
return true;
|
|
15780
|
+
const v4 = host.match(/^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/);
|
|
15781
|
+
if (!v4)
|
|
15782
|
+
return false;
|
|
15783
|
+
const [a, b] = [Number(v4[1]), Number(v4[2])];
|
|
15784
|
+
if (a === 10)
|
|
15785
|
+
return true;
|
|
15786
|
+
if (a === 127)
|
|
15787
|
+
return true;
|
|
15788
|
+
if (a === 192 && b === 168)
|
|
15789
|
+
return true;
|
|
15790
|
+
if (a === 172 && b >= 16 && b <= 31)
|
|
15791
|
+
return true;
|
|
15792
|
+
if (a === 169 && b === 254)
|
|
15793
|
+
return true;
|
|
15794
|
+
return false;
|
|
15795
|
+
}
|
|
15796
|
+
|
|
15797
|
+
// src/setup/hindsight-context-budget.ts
|
|
15798
|
+
function clamp(value, floor, ceiling) {
|
|
15799
|
+
return Math.min(ceiling, Math.max(floor, value));
|
|
15800
|
+
}
|
|
15801
|
+
function usableContextTokens(windowTokens) {
|
|
15802
|
+
return windowTokens - Math.floor(windowTokens * HINDSIGHT_CONTEXT_SAFETY_FRACTION);
|
|
15803
|
+
}
|
|
15804
|
+
function defaultContextWindowForProvider(provider, baseUrl) {
|
|
15805
|
+
const url = baseUrl?.trim();
|
|
15806
|
+
if (url && isSelfHostedHttpUrl(url))
|
|
15807
|
+
return HINDSIGHT_CONSERVATIVE_CONTEXT_WINDOW;
|
|
15808
|
+
const p = provider.trim().toLowerCase();
|
|
15809
|
+
if (p === "claude-code" || p === "anthropic")
|
|
15810
|
+
return HINDSIGHT_CLAUDE_CONTEXT_WINDOW;
|
|
15811
|
+
return HINDSIGHT_CONSERVATIVE_CONTEXT_WINDOW;
|
|
15812
|
+
}
|
|
15813
|
+
function resolveLaneContextWindow(lane, llm) {
|
|
15814
|
+
const perOp = llm?.[lane];
|
|
15815
|
+
const provider = perOp?.provider?.trim() || llm?.provider?.trim() || "claude-code";
|
|
15816
|
+
const baseUrl = perOp?.base_url?.trim() || undefined;
|
|
15817
|
+
const perOpWindow = perOp?.context_window;
|
|
15818
|
+
if (typeof perOpWindow === "number" && perOpWindow > 0) {
|
|
15819
|
+
return { windowTokens: Math.floor(perOpWindow), windowSource: "per-op", provider, baseUrl };
|
|
15820
|
+
}
|
|
15821
|
+
const globalWindow = llm?.context_window;
|
|
15822
|
+
if (typeof globalWindow === "number" && globalWindow > 0) {
|
|
15823
|
+
return { windowTokens: Math.floor(globalWindow), windowSource: "global", provider, baseUrl };
|
|
15824
|
+
}
|
|
15825
|
+
return {
|
|
15826
|
+
windowTokens: defaultContextWindowForProvider(provider, baseUrl),
|
|
15827
|
+
windowSource: "provider-default",
|
|
15828
|
+
provider,
|
|
15829
|
+
baseUrl
|
|
15830
|
+
};
|
|
15831
|
+
}
|
|
15832
|
+
function resolveHindsightContextBudget(llm) {
|
|
15833
|
+
const cons = resolveLaneContextWindow("consolidation", llm);
|
|
15834
|
+
const ret = resolveLaneContextWindow("retain", llm);
|
|
15835
|
+
const consMaxCompletion = clamp(Math.floor(cons.windowTokens / 4), HINDSIGHT_CONSOLIDATION_MAX_COMPLETION_FLOOR, HINDSIGHT_CONSOLIDATION_MAX_COMPLETION_CEILING);
|
|
15836
|
+
const consUsable = usableContextTokens(cons.windowTokens);
|
|
15837
|
+
const consPromptBudget = consUsable - consMaxCompletion;
|
|
15838
|
+
const batchSize = clamp(Math.floor((consPromptBudget - HINDSIGHT_CONSOLIDATION_PROMPT_OVERHEAD_TOKENS) / HINDSIGHT_CONSOLIDATION_TOKENS_PER_FACT), HINDSIGHT_CONSOLIDATION_BATCH_SIZE_FLOOR, HINDSIGHT_CONSOLIDATION_BATCH_SIZE_CEILING);
|
|
15839
|
+
const consPrompt = HINDSIGHT_CONSOLIDATION_PROMPT_OVERHEAD_TOKENS + batchSize * HINDSIGHT_CONSOLIDATION_TOKENS_PER_FACT;
|
|
15840
|
+
const retMaxCompletion = clamp(Math.floor(ret.windowTokens * 3 / 16), HINDSIGHT_RETAIN_MAX_COMPLETION_FLOOR, HINDSIGHT_RETAIN_MAX_COMPLETION_CEILING);
|
|
15841
|
+
const refl = resolveLaneContextWindow("reflect", llm);
|
|
15842
|
+
const reflCompletionReserve = clamp(Math.floor(refl.windowTokens * 3 / 16), HINDSIGHT_RETAIN_MAX_COMPLETION_FLOOR, HINDSIGHT_RETAIN_MAX_COMPLETION_CEILING);
|
|
15843
|
+
const reflUsable = usableContextTokens(refl.windowTokens);
|
|
15844
|
+
const reflMaxContext = Math.max(HINDSIGHT_REFLECT_MAX_CONTEXT_FLOOR, Math.floor((reflUsable - reflCompletionReserve) / 1000) * 1000);
|
|
15845
|
+
return {
|
|
15846
|
+
consolidation: {
|
|
15847
|
+
lane: "consolidation",
|
|
15848
|
+
windowTokens: cons.windowTokens,
|
|
15849
|
+
usableTokens: consUsable,
|
|
15850
|
+
windowSource: cons.windowSource,
|
|
15851
|
+
provider: cons.provider,
|
|
15852
|
+
batchSize,
|
|
15853
|
+
maxCompletionTokens: consMaxCompletion,
|
|
15854
|
+
estimatedPromptTokens: consPrompt,
|
|
15855
|
+
worstCaseTotalTokens: consPrompt + consMaxCompletion
|
|
15856
|
+
},
|
|
15857
|
+
reflect: {
|
|
15858
|
+
lane: "reflect",
|
|
15859
|
+
windowTokens: refl.windowTokens,
|
|
15860
|
+
usableTokens: reflUsable,
|
|
15861
|
+
windowSource: refl.windowSource,
|
|
15862
|
+
provider: refl.provider,
|
|
15863
|
+
maxContextTokens: reflMaxContext,
|
|
15864
|
+
completionReserveTokens: reflCompletionReserve,
|
|
15865
|
+
estimatedPromptTokens: reflMaxContext,
|
|
15866
|
+
worstCaseTotalTokens: reflMaxContext + reflCompletionReserve
|
|
15867
|
+
},
|
|
15868
|
+
retain: {
|
|
15869
|
+
lane: "retain",
|
|
15870
|
+
windowTokens: ret.windowTokens,
|
|
15871
|
+
usableTokens: usableContextTokens(ret.windowTokens),
|
|
15872
|
+
windowSource: ret.windowSource,
|
|
15873
|
+
provider: ret.provider,
|
|
15874
|
+
maxCompletionTokens: retMaxCompletion,
|
|
15875
|
+
estimatedPromptTokens: HINDSIGHT_RETAIN_PROMPT_ESTIMATE_TOKENS,
|
|
15876
|
+
worstCaseTotalTokens: HINDSIGHT_RETAIN_PROMPT_ESTIMATE_TOKENS + retMaxCompletion
|
|
15877
|
+
}
|
|
15878
|
+
};
|
|
15879
|
+
}
|
|
15880
|
+
function laneCheck(b) {
|
|
15881
|
+
return { ...b, completionTokens: b.maxCompletionTokens, completionLabel: "completion" };
|
|
15882
|
+
}
|
|
15883
|
+
function reflectLaneCheck(b) {
|
|
15884
|
+
return {
|
|
15885
|
+
...b,
|
|
15886
|
+
completionTokens: b.completionReserveTokens,
|
|
15887
|
+
completionLabel: "completion reserve"
|
|
15888
|
+
};
|
|
15889
|
+
}
|
|
15890
|
+
function laneFailure(b) {
|
|
15891
|
+
if (b.worstCaseTotalTokens > b.usableTokens) {
|
|
15892
|
+
return `hindsight ${b.lane}: worst-case ${b.worstCaseTotalTokens} tokens ` + `(${b.estimatedPromptTokens} prompt + ${b.completionTokens} ${b.completionLabel}) ` + `exceeds the ${b.usableTokens} usable tokens of ` + `the declared ${b.windowTokens}-token context window ` + `(${Math.round(HINDSIGHT_CONTEXT_SAFETY_FRACTION * 100)}% safety band held back; ` + `source: ${b.windowSource}, provider: ${b.provider}).`;
|
|
15893
|
+
}
|
|
15894
|
+
if (b.lane === "retain" && b.maxCompletionTokens !== undefined && b.maxCompletionTokens <= HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE) {
|
|
15895
|
+
return `hindsight retain: derived max_completion_tokens ${b.maxCompletionTokens} is not ` + `greater than the upstream retain_chunk_size ${HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE}; ` + `the hindsight container refuses to boot with this combination.`;
|
|
15896
|
+
}
|
|
15897
|
+
return;
|
|
15898
|
+
}
|
|
15899
|
+
function assertHindsightContextBudgetFits(budget) {
|
|
15900
|
+
for (const lane of [
|
|
15901
|
+
laneCheck(budget.consolidation),
|
|
15902
|
+
laneCheck(budget.retain),
|
|
15903
|
+
reflectLaneCheck(budget.reflect)
|
|
15904
|
+
]) {
|
|
15905
|
+
const failure = laneFailure(lane);
|
|
15906
|
+
if (failure) {
|
|
15907
|
+
throw new HindsightContextBudgetError(lane.lane, `${failure}
|
|
15908
|
+
` + `A local backend does NOT error on context overflow \u2014 llama.cpp context-shift ` + `silently drops the system prompt and returns HTTP 200 with conversational text ` + `instead of the required JSON, so this must be caught here.
|
|
15909
|
+
` + `Fix: raise \`hindsight.llm.context_window\` (or \`hindsight.llm.${lane.lane}.context_window\`) ` + `to the backend's real window, or point the lane at a larger-window model.`);
|
|
15910
|
+
}
|
|
15911
|
+
}
|
|
15912
|
+
}
|
|
15913
|
+
function resolveCheckedHindsightContextBudget(llm) {
|
|
15914
|
+
const budget = resolveHindsightContextBudget(llm);
|
|
15915
|
+
assertHindsightContextBudgetFits(budget);
|
|
15916
|
+
return budget;
|
|
15917
|
+
}
|
|
15918
|
+
var HINDSIGHT_CLAUDE_CONTEXT_WINDOW = 200000, HINDSIGHT_CONSERVATIVE_CONTEXT_WINDOW = 32768, HINDSIGHT_CONTEXT_SAFETY_FRACTION = 0.2, HINDSIGHT_CONSOLIDATION_PROMPT_OVERHEAD_TOKENS = 2270, HINDSIGHT_CONSOLIDATION_TOKENS_PER_FACT = 2500, HINDSIGHT_RETAIN_PROMPT_ESTIMATE_TOKENS = 8000, HINDSIGHT_CONSOLIDATION_BATCH_SIZE_CEILING = 12, HINDSIGHT_CONSOLIDATION_BATCH_SIZE_FLOOR = 1, HINDSIGHT_CONSOLIDATION_MAX_COMPLETION_CEILING = 16384, HINDSIGHT_RETAIN_MAX_COMPLETION_CEILING = 16384, HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE = 3000, HINDSIGHT_CONSOLIDATION_MAX_COMPLETION_FLOOR = 1024, HINDSIGHT_RETAIN_MAX_COMPLETION_FLOOR, HINDSIGHT_REFLECT_MAX_CONTEXT_FLOOR = 2048, HindsightContextBudgetError;
|
|
15919
|
+
var init_hindsight_context_budget = __esm(() => {
|
|
15920
|
+
HINDSIGHT_RETAIN_MAX_COMPLETION_FLOOR = HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE + 72;
|
|
15921
|
+
HindsightContextBudgetError = class HindsightContextBudgetError extends Error {
|
|
15922
|
+
lane;
|
|
15923
|
+
constructor(lane, message) {
|
|
15924
|
+
super(message);
|
|
15925
|
+
this.name = "HindsightContextBudgetError";
|
|
15926
|
+
this.lane = lane;
|
|
15927
|
+
}
|
|
15928
|
+
};
|
|
15929
|
+
});
|
|
15930
|
+
|
|
15734
15931
|
// src/util/atomic.ts
|
|
15735
15932
|
var exports_atomic = {};
|
|
15736
15933
|
__export(exports_atomic, {
|
|
@@ -15854,8 +16051,9 @@ function hindsightInteractiveLlmTimeoutSeconds() {
|
|
|
15854
16051
|
function hindsightConsolidationLlmTimeoutSeconds() {
|
|
15855
16052
|
return clientBudgetSeconds(LITELLM_TIMEOUT_TIERS.consolidation);
|
|
15856
16053
|
}
|
|
15857
|
-
function hindsightLlmBudgetEnv() {
|
|
15858
|
-
const
|
|
16054
|
+
function hindsightLlmBudgetEnv(llm) {
|
|
16055
|
+
const contextBudget = resolveCheckedHindsightContextBudget(llm);
|
|
16056
|
+
const maxCompletionTokens = Math.min(HINDSIGHT_DEFAULT_RETAIN_MAX_COMPLETION_TOKENS, contextBudget.retain.maxCompletionTokens);
|
|
15859
16057
|
const interactiveS = hindsightInteractiveLlmTimeoutSeconds();
|
|
15860
16058
|
const retainS = hindsightRetainClientTimeoutSeconds();
|
|
15861
16059
|
const consolidationS = hindsightConsolidationLlmTimeoutSeconds();
|
|
@@ -15885,7 +16083,16 @@ function hindsightLlmBudgetEnv() {
|
|
|
15885
16083
|
["HINDSIGHT_API_LLM_TIMEOUT", String(interactiveS)],
|
|
15886
16084
|
["HINDSIGHT_API_REFLECT_LLM_TIMEOUT", String(interactiveS)],
|
|
15887
16085
|
["HINDSIGHT_API_RETAIN_LLM_TIMEOUT", String(retainS)],
|
|
15888
|
-
["HINDSIGHT_API_CONSOLIDATION_LLM_TIMEOUT", String(consolidationS)]
|
|
16086
|
+
["HINDSIGHT_API_CONSOLIDATION_LLM_TIMEOUT", String(consolidationS)],
|
|
16087
|
+
["HINDSIGHT_API_CONSOLIDATION_LLM_BATCH_SIZE", String(contextBudget.consolidation.batchSize)],
|
|
16088
|
+
[
|
|
16089
|
+
"HINDSIGHT_API_CONSOLIDATION_MAX_COMPLETION_TOKENS",
|
|
16090
|
+
String(contextBudget.consolidation.maxCompletionTokens)
|
|
16091
|
+
],
|
|
16092
|
+
[
|
|
16093
|
+
"HINDSIGHT_API_REFLECT_MAX_CONTEXT_TOKENS",
|
|
16094
|
+
String(contextBudget.reflect.maxContextTokens)
|
|
16095
|
+
]
|
|
15889
16096
|
];
|
|
15890
16097
|
}
|
|
15891
16098
|
function isPortFree(port) {
|
|
@@ -16014,15 +16221,6 @@ function resolveHindsightLlm(llm, litellm) {
|
|
|
16014
16221
|
const model = llm?.model?.trim() || (litellm ? litellm.model ?? HINDSIGHT_DEFAULT_LITELLM_MODEL : HINDSIGHT_DEFAULT_MODEL);
|
|
16015
16222
|
return { provider, model };
|
|
16016
16223
|
}
|
|
16017
|
-
function isLoopbackHttpUrl(url) {
|
|
16018
|
-
try {
|
|
16019
|
-
const u = new URL(url.includes("://") ? url : `http://${url}`);
|
|
16020
|
-
const h = (u.hostname || "").toLowerCase().replace(/^\[|\]$/g, "");
|
|
16021
|
-
return h === "localhost" || h === "127.0.0.1" || h === "::1";
|
|
16022
|
-
} catch {
|
|
16023
|
-
return false;
|
|
16024
|
-
}
|
|
16025
|
-
}
|
|
16026
16224
|
function collectHindsightLlmBaseUrls(llm, litellm) {
|
|
16027
16225
|
const out = [];
|
|
16028
16226
|
const seen = new Set;
|
|
@@ -16045,40 +16243,6 @@ function hindsightNeedsHostNetwork(llm, litellm) {
|
|
|
16045
16243
|
return true;
|
|
16046
16244
|
return collectHindsightLlmBaseUrls(llm).some(isLoopbackHttpUrl);
|
|
16047
16245
|
}
|
|
16048
|
-
function isSelfHostedHttpUrl(url) {
|
|
16049
|
-
let host;
|
|
16050
|
-
try {
|
|
16051
|
-
const u = new URL(url.includes("://") ? url : `http://${url}`);
|
|
16052
|
-
host = (u.hostname || "").toLowerCase().replace(/^\[|\]$/g, "");
|
|
16053
|
-
} catch {
|
|
16054
|
-
return false;
|
|
16055
|
-
}
|
|
16056
|
-
if (!host)
|
|
16057
|
-
return false;
|
|
16058
|
-
if (isLoopbackHttpUrl(url))
|
|
16059
|
-
return true;
|
|
16060
|
-
if (host === "host.docker.internal" || host === "gateway.docker.internal")
|
|
16061
|
-
return true;
|
|
16062
|
-
if (host.endsWith(".local") || host.endsWith(".internal"))
|
|
16063
|
-
return true;
|
|
16064
|
-
if (/^f[cd][0-9a-f]{2}:/.test(host) || /^fe[89ab][0-9a-f]:/.test(host))
|
|
16065
|
-
return true;
|
|
16066
|
-
const v4 = host.match(/^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/);
|
|
16067
|
-
if (!v4)
|
|
16068
|
-
return false;
|
|
16069
|
-
const [a, b] = [Number(v4[1]), Number(v4[2])];
|
|
16070
|
-
if (a === 10)
|
|
16071
|
-
return true;
|
|
16072
|
-
if (a === 127)
|
|
16073
|
-
return true;
|
|
16074
|
-
if (a === 192 && b === 168)
|
|
16075
|
-
return true;
|
|
16076
|
-
if (a === 172 && b >= 16 && b <= 31)
|
|
16077
|
-
return true;
|
|
16078
|
-
if (a === 169 && b === 254)
|
|
16079
|
-
return true;
|
|
16080
|
-
return false;
|
|
16081
|
-
}
|
|
16082
16246
|
function hindsightLocalLlmEnabled(llm, litellm, override) {
|
|
16083
16247
|
if (override !== undefined)
|
|
16084
16248
|
return override;
|
|
@@ -16140,13 +16304,11 @@ function startHindsight(ports, litellm, imageTag, llm, mirrorDir, gpu, perf) {
|
|
|
16140
16304
|
`HINDSIGHT_API_RECALL_MAX_CONCURRENT=${HINDSIGHT_DEFAULT_RECALL_MAX_CONCURRENT}`,
|
|
16141
16305
|
"-e",
|
|
16142
16306
|
`HINDSIGHT_API_REFLECT_WALL_TIMEOUT=${HINDSIGHT_DEFAULT_REFLECT_WALL_TIMEOUT_S}`,
|
|
16143
|
-
...hindsightLlmBudgetEnv().flatMap(([k, v]) => ["-e", `${k}=${v}`]),
|
|
16144
|
-
"-e",
|
|
16145
|
-
`HINDSIGHT_API_CONSOLIDATION_LLM_BATCH_SIZE=${HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_BATCH_SIZE}`,
|
|
16307
|
+
...hindsightLlmBudgetEnv(llm).flatMap(([k, v]) => ["-e", `${k}=${v}`]),
|
|
16146
16308
|
"-e",
|
|
16147
16309
|
`HINDSIGHT_API_WORKER_CONSOLIDATION_MAX_SLOTS=${HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_SLOTS}`,
|
|
16148
16310
|
"-e",
|
|
16149
|
-
`
|
|
16311
|
+
`HINDSIGHT_API_WORKER_CONSOLIDATION_SLOT_LIMIT=${HINDSIGHT_DEFAULT_CONSOLIDATION_SLOT_LIMIT}`,
|
|
16150
16312
|
"-e",
|
|
16151
16313
|
`HINDSIGHT_API_CONSOLIDATION_MAX_MEMORIES_PER_ROUND=${HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_MEMORIES_PER_ROUND}`,
|
|
16152
16314
|
"-e",
|
|
@@ -16375,10 +16537,9 @@ function generateHindsightComposeSnippet(llm, mirrorDir, litellm, gpu, perf) {
|
|
|
16375
16537
|
` - HINDSIGHT_API_RERANKER_LOCAL_MAX_CONCURRENT=${HINDSIGHT_DEFAULT_RERANKER_LOCAL_MAX_CONCURRENT}`,
|
|
16376
16538
|
` - HINDSIGHT_API_RECALL_MAX_CONCURRENT=${HINDSIGHT_DEFAULT_RECALL_MAX_CONCURRENT}`,
|
|
16377
16539
|
` - HINDSIGHT_API_REFLECT_WALL_TIMEOUT=${HINDSIGHT_DEFAULT_REFLECT_WALL_TIMEOUT_S}`,
|
|
16378
|
-
...hindsightLlmBudgetEnv().map(([k, v]) => ` - ${k}=${v}`),
|
|
16379
|
-
` - HINDSIGHT_API_CONSOLIDATION_LLM_BATCH_SIZE=${HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_BATCH_SIZE}`,
|
|
16540
|
+
...hindsightLlmBudgetEnv(llm).map(([k, v]) => ` - ${k}=${v}`),
|
|
16380
16541
|
` - HINDSIGHT_API_WORKER_CONSOLIDATION_MAX_SLOTS=${HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_SLOTS}`,
|
|
16381
|
-
` -
|
|
16542
|
+
` - HINDSIGHT_API_WORKER_CONSOLIDATION_SLOT_LIMIT=${HINDSIGHT_DEFAULT_CONSOLIDATION_SLOT_LIMIT}`,
|
|
16382
16543
|
` - HINDSIGHT_API_CONSOLIDATION_MAX_MEMORIES_PER_ROUND=${HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_MEMORIES_PER_ROUND}`,
|
|
16383
16544
|
` - HINDSIGHT_API_WORKER_ID=${HINDSIGHT_DEFAULT_WORKER_ID}`,
|
|
16384
16545
|
...hindsightPerfEnvPairs(llm, litellm, gpu, perf).map(([k, v]) => ` - ${k}=${v}`),
|
|
@@ -16481,7 +16642,7 @@ async function ensureHindsightConsumer(configPath, account, uid = HINDSIGHT_DEFA
|
|
|
16481
16642
|
atomicWriteFileSync2(configPath, tail, mode);
|
|
16482
16643
|
return { added: true, reason: "added" };
|
|
16483
16644
|
}
|
|
16484
|
-
var HINDSIGHT_DEFAULT_API_PORT = 18888, HINDSIGHT_DEFAULT_UI_PORT = 9999, HINDSIGHT_DEFAULT_MCP_URL, HINDSIGHT_DEFAULT_API_BASE_URL, HINDSIGHT_DEFAULT_MAX_OBSERVATIONS_PER_SCOPE = 1000, HINDSIGHT_CONSUMER_NAME = "hindsight", HINDSIGHT_DEFAULT_WORKER_ID = "switchroom-hindsight", HINDSIGHT_DATA_VOLUME = "switchroom-hindsight-data", HINDSIGHT_DEFAULT_UID = 11000, HINDSIGHT_IMAGE_REPO = "ghcr.io/switchroom/switchroom-hindsight", HINDSIGHT_IMAGE, HINDSIGHT_DEFAULT_MODEL = "claude-sonnet-5", HINDSIGHT_DEFAULT_LITELLM_MODEL = "openrouter/google/gemini-3.1-flash-lite", HINDSIGHT_DEFAULT_MCP_STATELESS = true, HINDSIGHT_BROKER_SOCK_VOLUME, HINDSIGHT_CREDS_MIRROR_VOLUME, HINDSIGHT_CRED_DIR = "/run/claude-creds", HINDSIGHT_DEFAULT_RERANKER_BUCKET_BATCHING = "true", HINDSIGHT_DEFAULT_RERANKER_MAX_CANDIDATES = 150, HINDSIGHT_DEFAULT_RERANKER_LOCAL_MAX_CONCURRENT = 4, HINDSIGHT_DEFAULT_RECALL_MAX_CONCURRENT = 8, HINDSIGHT_DEFAULT_REFLECT_WALL_TIMEOUT_S = 600, HINDSIGHT_RETAIN_CHUNK_SIZE = 3000, HINDSIGHT_DEFAULT_RETAIN_MAX_COMPLETION_TOKENS = 16384, HINDSIGHT_RETAIN_MIN_TOKENS_PER_SECOND = 80.6, HINDSIGHT_RETAIN_CLIENT_DEADLINE_S,
|
|
16645
|
+
var HINDSIGHT_DEFAULT_API_PORT = 18888, HINDSIGHT_DEFAULT_UI_PORT = 9999, HINDSIGHT_DEFAULT_MCP_URL, HINDSIGHT_DEFAULT_API_BASE_URL, HINDSIGHT_DEFAULT_MAX_OBSERVATIONS_PER_SCOPE = 1000, HINDSIGHT_CONSUMER_NAME = "hindsight", HINDSIGHT_DEFAULT_WORKER_ID = "switchroom-hindsight", HINDSIGHT_DATA_VOLUME = "switchroom-hindsight-data", HINDSIGHT_DEFAULT_UID = 11000, HINDSIGHT_IMAGE_REPO = "ghcr.io/switchroom/switchroom-hindsight", HINDSIGHT_IMAGE, HINDSIGHT_DEFAULT_MODEL = "claude-sonnet-5", HINDSIGHT_DEFAULT_LITELLM_MODEL = "openrouter/google/gemini-3.1-flash-lite", HINDSIGHT_DEFAULT_MCP_STATELESS = true, HINDSIGHT_BROKER_SOCK_VOLUME, HINDSIGHT_CREDS_MIRROR_VOLUME, HINDSIGHT_CRED_DIR = "/run/claude-creds", HINDSIGHT_DEFAULT_RERANKER_BUCKET_BATCHING = "true", HINDSIGHT_DEFAULT_RERANKER_MAX_CANDIDATES = 150, HINDSIGHT_DEFAULT_RERANKER_LOCAL_MAX_CONCURRENT = 4, HINDSIGHT_DEFAULT_RECALL_MAX_CONCURRENT = 8, HINDSIGHT_DEFAULT_REFLECT_WALL_TIMEOUT_S = 600, HINDSIGHT_RETAIN_CHUNK_SIZE = 3000, HINDSIGHT_DEFAULT_RETAIN_MAX_COMPLETION_TOKENS = 16384, HINDSIGHT_RETAIN_MIN_TOKENS_PER_SECOND = 80.6, HINDSIGHT_RETAIN_CLIENT_DEADLINE_S, HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_SLOTS = 1, HINDSIGHT_DEFAULT_CONSOLIDATION_MAX_MEMORIES_PER_ROUND = 500, HINDSIGHT_DEFAULT_CONSOLIDATION_SLOT_LIMIT = 6, HINDSIGHT_DEFAULT_MEM_LIMIT = "8g", HINDSIGHT_DEFAULT_MEM_RESERVATION = "4g", HINDSIGHT_DEFAULT_PIDS_LIMIT = 1000, HINDSIGHT_DEFAULT_SHM_SIZE = "2g", HINDSIGHT_HEALTHCHECK_PY = 'import urllib.request,sys; sys.exit(0 if urllib.request.urlopen("http://localhost:8888/health",timeout=4).getcode()==200 else 1)', HINDSIGHT_HEALTHCHECK_CMD, DOCKER_PROBE_TIMEOUT_MS, defaultDockerProbe = (args) => {
|
|
16485
16646
|
try {
|
|
16486
16647
|
return execFileSync("docker", args, {
|
|
16487
16648
|
stdio: "pipe",
|
|
@@ -16499,6 +16660,8 @@ var init_hindsight = __esm(() => {
|
|
|
16499
16660
|
init_host_capabilities();
|
|
16500
16661
|
init_hindsight_perf_defaults();
|
|
16501
16662
|
init_hindsight_pg_defaults();
|
|
16663
|
+
init_hindsight_context_budget();
|
|
16664
|
+
init_hindsight_perf_defaults();
|
|
16502
16665
|
HINDSIGHT_DEFAULT_MCP_URL = `http://127.0.0.1:${HINDSIGHT_DEFAULT_API_PORT}/mcp/`;
|
|
16503
16666
|
HINDSIGHT_DEFAULT_API_BASE_URL = HINDSIGHT_DEFAULT_MCP_URL.replace(/\/mcp\/?$/, "");
|
|
16504
16667
|
HINDSIGHT_IMAGE = `${HINDSIGHT_IMAGE_REPO}:latest`;
|
|
@@ -28932,7 +29095,7 @@ function buildSettingsHooksBlock(p) {
|
|
|
28932
29095
|
` + ` - Question with a short answer \u2192 just reply with the answer.
|
|
28933
29096
|
` + " - Complex tool-driven work \u2192 go straight to the tools (the " + "compose-area preview is the ambient liveness signal), then reply " + 'once with the answer or a genuine mid-work pivot ("halfway ' + 'through \u2014 found an unexpected issue, want me to continue?"). Not ' + `"still working".
|
|
28934
29097
|
|
|
28935
|
-
` + "
|
|
29098
|
+
` + "LABEL THE WORK AS YOU DO IT. The user watches a live preview built " + "from your tool activity, so what you put in a tool call is what they " + "read. Two output requirements. FIRST: every Bash and tool call gets a " + 'plain-English `description` naming the goal \u2014 "Checking the gateway ' + 'logs to find why the turn stalled", never raw tool names ("calling ' + 'Bash", "Read(x)") and never a debug dump. That description, not the ' + "raw command, is what the user sees. SECOND: before a long stretch of " + "work, post ONE short status line saying what you are starting \u2014 one " + "line per stretch, in plain words. Emit it as the `description` on the " + "first tool call of the stretch, or as a status line through the " + "progress tool where you have one; do NOT leave it sitting as unsent " + "transcript text (see the reply rule below). This labelling is the ONE " + "thing to keep doing; it is NOT the placeholder ack banned above (that " + `is a chat reply, which you still skip).
|
|
28936
29099
|
|
|
28937
29100
|
` + 'Do NOT send a trailing confirmation after your answer \u2014 no "Done.", ' + '"Sent.", "Hope that helps." as a separate message once you have ' + "already replied. Your answer is the last thing the user should " + `see; a follow-up "Done." is dead-air clutter (and the user's ` + `device already pinged on the answer). Stop after the answer.
|
|
28938
29101
|
|
|
@@ -28942,7 +29105,7 @@ function buildSettingsHooksBlock(p) {
|
|
|
28942
29105
|
|
|
28943
29106
|
` + "TURN-END SHAPE: the human reads your turn-end on a phone. Build it " + "for a thumb, not a terminal. LEAD WITH THE ONE DECISION OR ANSWER " + "in the first line \u2014 the single thing the user has to know. A routine " + "turn-end is a FEW SHORT LINES, not a multi-section report; if you " + "find yourself writing more than ~6 lines or stacking labelled " + "sections, you are dumping, not answering. ONE IDEA PER MESSAGE: " + "split genuinely separate topics into separate replies rather than " + "piling sections into one bubble. Push detail BELOW the answer or " + 'leave it out \u2014 offer "want the detail?" instead of pre-emptively ' + "dumping logs, full file contents, or a section per thread you " + "touched. RESERVE the long multi-section structured message for when " + 'the operator EXPLICITLY asked to go deep ("full breakdown", "walk me ' + 'through it", "show everything"). Default to short; expand on ' + "request. A wall of text the user has to re-read to find the one fact " + `that matters is the failure this exists to prevent.
|
|
28944
29107
|
|
|
28945
|
-
` + 'CRITICAL: "answer" means a call to the reply tool ' + "(mcp__switchroom-telegram__reply). " + "Your terminal/transcript text is NEVER delivered to Telegram \u2014 the " + "user sees only what you send through the reply tool. After a long " + "tool sequence (scheduling, multi-step research, sub-agent handback), " + "do not let your closing narration stand as the answer: end the turn " + "by passing that narration to the reply tool. No reply tool call = the " + "user got nothing, however much text you wrote. Call the reply tool as " + "your FIRST action when you have the answer \u2014 do not write it out as " + "transcript text first and call reply afterward: a framework backstop " + "flushes unsent text after a delay and then your real reply lands late " + "and out of order
|
|
29108
|
+
` + 'CRITICAL: "answer" means a call to the reply tool ' + "(mcp__switchroom-telegram__reply). " + "Your terminal/transcript text is NEVER delivered to Telegram \u2014 the " + "user sees only what you send through the reply tool. After a long " + "tool sequence (scheduling, multi-step research, sub-agent handback), " + "do not let your closing narration stand as the answer: end the turn " + "by passing that narration to the reply tool. No reply tool call = the " + "user got nothing, however much text you wrote. Call the reply tool as " + "your FIRST action when you have the answer \u2014 do not write it out as " + "transcript text first and call reply afterward: a framework backstop " + "flushes unsent text after a delay and then your real reply lands late " + "and out of order. This is why the work-labelling above rides on tool " + "`description`s rather than loose prose: a tool description reaches the " + "preview immediately and is never subject to that flush, so there is " + "exactly one rule \u2014 user-facing text goes through a tool call, always." + "</turn-pacing>";
|
|
28946
29109
|
const switchroomUserPromptSubmit = [
|
|
28947
29110
|
...useHotReloadStable ? [
|
|
28948
29111
|
{
|
|
@@ -30000,22 +30163,19 @@ messaging a capable colleague \u2014 not a tool emitting output. Five beats:
|
|
|
30000
30163
|
compose the full answer. This holds even for a pure-thinking
|
|
30001
30164
|
answer: if it will run to a paragraph, ack first. It is the line
|
|
30002
30165
|
between a colleague and a black box.
|
|
30003
|
-
2. **Then go quiet and work \u2014 but
|
|
30166
|
+
2. **Then go quiet and work \u2014 but label what you are doing.** Heads-down
|
|
30004
30167
|
is correct: do NOT narrate every tool call, and a typing indicator
|
|
30005
|
-
runs automatically (you do not maintain it).
|
|
30006
|
-
|
|
30007
|
-
|
|
30008
|
-
|
|
30009
|
-
|
|
30010
|
-
|
|
30011
|
-
|
|
30012
|
-
|
|
30013
|
-
|
|
30014
|
-
|
|
30015
|
-
|
|
30016
|
-
When a step is a \`Bash\` command, always give it a plain-English
|
|
30017
|
-
\`description\` naming the goal \u2014 that description, not the raw command,
|
|
30018
|
-
is what the user sees.
|
|
30168
|
+
runs automatically (you do not maintain it). What you SHOULD do is
|
|
30169
|
+
make the work legible through the tool calls themselves: always give a
|
|
30170
|
+
\`Bash\` (or any tool) call a plain-English \`description\` naming the
|
|
30171
|
+
goal \u2014 "Checking the gateway logs to find why the turn stalled". That
|
|
30172
|
+
description, not the raw command, is what the user sees in the live
|
|
30173
|
+
preview. Before a long silent stretch, put one short status line there
|
|
30174
|
+
too, saying what you are starting. One line per stretch, plain words,
|
|
30175
|
+
never raw tool names ("calling Bash") or debug dumps. It is the
|
|
30176
|
+
difference between the user seeing "checking the logs to find the
|
|
30177
|
+
stall" and seeing a black box. Keep it in the tool call \u2014 loose
|
|
30178
|
+
transcript prose is not delivered and can be flushed late (see beat 5).
|
|
30019
30179
|
3. **Surface meaningful progress** at genuine inflection points \u2014 a
|
|
30020
30180
|
hard step finished, a blocker, a pivot, dispatching a sub-agent, a
|
|
30021
30181
|
notably slow wait, a finding worth knowing now. One short \`reply\`,
|
|
@@ -19434,17 +19434,19 @@ var HindsightPerOpLlmSchema = exports_external.object({
|
|
|
19434
19434
|
model: exports_external.string().min(1).optional().describe("Per-op model (upstream `HINDSIGHT_API_<OP>_LLM_MODEL`). Absent → " + "inherit the global `hindsight.llm.model`."),
|
|
19435
19435
|
provider: exports_external.string().min(1).optional().describe("Per-op provider (upstream `HINDSIGHT_API_<OP>_LLM_PROVIDER`). " + "Absent → inherit the global `hindsight.llm.provider`."),
|
|
19436
19436
|
base_url: exports_external.string().min(1).optional().describe("Per-op base URL (upstream `HINDSIGHT_API_<OP>_LLM_BASE_URL`). " + "Optional passthrough; absent → inherit the global."),
|
|
19437
|
-
api_key: exports_external.string().min(1).optional().describe("Per-op API key (upstream `HINDSIGHT_API_<OP>_LLM_API_KEY`). Literal " + "or `vault:` reference. Optional passthrough; absent → inherit global.")
|
|
19437
|
+
api_key: exports_external.string().min(1).optional().describe("Per-op API key (upstream `HINDSIGHT_API_<OP>_LLM_API_KEY`). Literal " + "or `vault:` reference. Optional passthrough; absent → inherit global."),
|
|
19438
|
+
context_window: exports_external.number().int().positive().optional().describe("Context window (tokens) of the backend serving THIS op. NOT an " + "upstream env var — switchroom derives the op's token budget " + "(consolidation batch size / max-completion caps / reflect " + "max-context cap) from it so a single call can never overflow the " + "window. Absent → inherit " + "`hindsight.llm.context_window`, else a per-provider default " + "(conservative for non-`claude-code` providers, which usually mean " + "a local llama.cpp/Ollama slot; a self-hosted `base_url` — loopback, " + "RFC1918, `.local`/`.internal` — forces the conservative default too, " + "regardless of the provider NAME, since the endpoint is where the " + "traffic actually terminates). All three lanes (`retain`, " + "`reflect`, `consolidation`) are budgeted independently.")
|
|
19438
19439
|
}).describe("Per-operation LLM override. Every field optional; an unset field (or " + "an omitted op block) inherits the global `hindsight.llm.*`, which is " + "already the engine's fallback — switchroom emits only the vars set.");
|
|
19439
19440
|
var HindsightConfigSchema = exports_external.object({
|
|
19440
19441
|
llm: exports_external.object({
|
|
19441
19442
|
provider: exports_external.string().min(1).optional().describe("Hindsight LLM provider (upstream `HINDSIGHT_API_LLM_PROVIDER`). " + "Defaults to `claude-code` (subscription-honest, broker-fed OAuth). " + "Any litellm-routable provider the upstream image supports is valid. " + "Serves as the GLOBAL default for every op absent a per-op override."),
|
|
19442
19443
|
model: exports_external.string().min(1).optional().describe("Hindsight LLM model (upstream `HINDSIGHT_API_LLM_MODEL`). Defaults " + "to HINDSIGHT_DEFAULT_MODEL. Any model your LiteLLM proxy can route " + "is valid, e.g. `openrouter/z-ai/glm-5.2` when routing through the " + "fleet proxy. With provider=claude-code this value is ALSO exported " + "as `ANTHROPIC_MODEL` to the claude subprocess. Serves as the GLOBAL " + "default for every op absent a per-op override."),
|
|
19444
|
+
context_window: exports_external.number().int().positive().optional().describe("GLOBAL context window (tokens) of the backend serving hindsight's " + "LLM ops — the declared size switchroom derives every token budget " + "from. Set this to the real window of whatever you point " + "`hindsight.llm` at (e.g. 32768 for a llama.cpp slot launched with " + "`-c 65536 -np 2`, 131072 for a large-window OpenRouter model). " + "Absent → a per-provider default: 200000 for `claude-code`, a " + "conservative 32768 for everything else. Overflowing a local " + "backend's window does NOT error — llama.cpp context-shift silently " + "drops the system prompt and the model answers conversationally " + "with HTTP 200 — so this value is what makes the failure " + "detectable at setup time instead of never."),
|
|
19443
19445
|
retain: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `retain` LLM op (memory ingestion). Emits " + "`HINDSIGHT_API_RETAIN_LLM_*`. Absent → uses the global model/provider."),
|
|
19444
19446
|
reflect: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `reflect` LLM op (synthesis / mental-model " + "refresh). Emits `HINDSIGHT_API_REFLECT_LLM_*`. Absent → uses global."),
|
|
19445
19447
|
consolidation: HindsightPerOpLlmSchema.optional().describe("Per-op override for the `consolidation` LLM op (background memory " + "merge). Emits `HINDSIGHT_API_CONSOLIDATION_LLM_*`. Absent → global.")
|
|
19446
19448
|
}).optional().describe("LLM knob for the hindsight container. The flat `provider`/`model` set " + "the global default (backward-compatible); optional `retain`/`reflect`/" + "`consolidation` blocks override individual ops. All fields optional; " + "unset fields fall back to the hard-coded defaults."),
|
|
19447
|
-
env: exports_external.record(exports_external.union([exports_external.string(), exports_external.number(), exports_external.boolean()])).optional().describe("Operator overrides for switchroom's capability-gated Hindsight " + "performance defaults. Only the keys switchroom actually manages are " + "honoured (`HINDSIGHT_PERF_ENV_KEYS` in " + "src/setup/hindsight-perf-defaults.ts: RERANKER_LOCAL_FP16, " + "LLM_MAX_CONCURRENT, RETAIN/CONSOLIDATION_LLM_MAX_CONCURRENT, " + "RECALL_MAX_CANDIDATES_PER_SOURCE, LINK_EXPANSION_PER_ENTITY_LIMIT, " + "LINK_EXPANSION_TIMEOUT, LLM_REASONING_EFFORT), plus the " + "embedded-PostgreSQL (pg0) sizing keys switchroom manages in " + "src/setup/hindsight-pg-defaults.ts (`HINDSIGHT_PG_ENV_KEYS`: " + "SWITCHROOM_HINDSIGHT_PG_EFFECTIVE_CACHE_SIZE, " + "SWITCHROOM_HINDSIGHT_PG_SHARED_BUFFERS — a postgres size string such " + "as `4GB`, or the sentinel `off` to leave pg0's own default for that " + "one knob). A value set here " + "REPLACES switchroom's default and is emitted even when the gating " + "capability is absent, so an operator can always force a knob. Other " + "`HINDSIGHT_API_*` keys are deliberately IGNORED — a blanket " + "passthrough would collide with the vars startHindsight() derives " + "itself (HINDSIGHT_API_PORT, the retain token/deadline budget).")
|
|
19449
|
+
env: exports_external.record(exports_external.union([exports_external.string(), exports_external.number(), exports_external.boolean()])).optional().describe("Operator overrides for switchroom's capability-gated Hindsight " + "performance defaults. Only the keys switchroom actually manages are " + "honoured (`HINDSIGHT_PERF_ENV_KEYS` in " + "src/setup/hindsight-perf-defaults.ts: RERANKER_LOCAL_FP16, " + "RERANKER_LOCAL_BATCH_SIZE, LLM_MAX_CONCURRENT, " + "RETAIN/CONSOLIDATION_LLM_MAX_CONCURRENT, LLM_STRICT_SCHEMA, " + "LLM_MAX_RETRIES, CONSOLIDATION_LLM_PARALLELISM, " + "RECALL_MAX_CANDIDATES_PER_SOURCE, LINK_EXPANSION_PER_ENTITY_LIMIT, " + "LINK_EXPANSION_TIMEOUT, LLM_REASONING_EFFORT), the override-only keys " + "switchroom manages but ships NO default for " + "(`HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS`: " + "HINDSIGHT_API_WORKER_CONSOLIDATION_BANK_PRIORITY — a per-deployment " + "`bank-pattern:priority,...` map; unset means upstream's flat " + "created_at FIFO across banks), plus the " + "embedded-PostgreSQL (pg0) sizing keys switchroom manages in " + "src/setup/hindsight-pg-defaults.ts (`HINDSIGHT_PG_ENV_KEYS`: " + "SWITCHROOM_HINDSIGHT_PG_EFFECTIVE_CACHE_SIZE, " + "SWITCHROOM_HINDSIGHT_PG_SHARED_BUFFERS — a postgres size string such " + "as `4GB`, or the sentinel `off` to leave pg0's own default for that " + "one knob). A value set here " + "REPLACES switchroom's default and is emitted even when the gating " + "capability is absent, so an operator can always force a knob. Other " + "`HINDSIGHT_API_*` keys are deliberately IGNORED — a blanket " + "passthrough would collide with the vars startHindsight() derives " + "itself (HINDSIGHT_API_PORT, the retain token/deadline budget).")
|
|
19448
19450
|
});
|
|
19449
19451
|
var MicrosoftWorkspaceConfigSchema = exports_external.object({
|
|
19450
19452
|
microsoft_client_id: exports_external.string().min(1).optional().describe("Microsoft OAuth application (client) ID from Entra portal " + "(literal string or vault reference e.g. " + "'vault:microsoft-oauth-client-id'). OPTIONAL — omit it to use " + "switchroom's shipped default Microsoft app (zero-config). " + "Set it only to bring your own Entra app (BYO)."),
|
|
@@ -21121,7 +21123,7 @@ function allocateAgentUid(name) {
|
|
|
21121
21123
|
}
|
|
21122
21124
|
|
|
21123
21125
|
// src/build-info.ts
|
|
21124
|
-
var VERSION = "0.19.
|
|
21126
|
+
var VERSION = "0.19.24";
|
|
21125
21127
|
|
|
21126
21128
|
// src/cli/agent-config.ts
|
|
21127
21129
|
import { join as join2 } from "node:path";
|
|
@@ -21224,6 +21226,10 @@ var HINDSIGHT_DEFAULT_LLM_MAX_CONCURRENT = 4;
|
|
|
21224
21226
|
var HINDSIGHT_DEFAULT_RETAIN_LLM_MAX_CONCURRENT = 1;
|
|
21225
21227
|
var HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_MAX_CONCURRENT = 1;
|
|
21226
21228
|
var HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16 = "true";
|
|
21229
|
+
var HINDSIGHT_DEFAULT_RERANKER_LOCAL_BATCH_SIZE = 128;
|
|
21230
|
+
var HINDSIGHT_DEFAULT_LLM_STRICT_SCHEMA = "true";
|
|
21231
|
+
var HINDSIGHT_DEFAULT_LLM_MAX_RETRIES = 2;
|
|
21232
|
+
var HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_PARALLELISM = 2;
|
|
21227
21233
|
var HINDSIGHT_PERF_DEFAULTS_UNGATED = [
|
|
21228
21234
|
[
|
|
21229
21235
|
"HINDSIGHT_API_RECALL_MAX_CANDIDATES_PER_SOURCE",
|
|
@@ -21237,10 +21243,18 @@ var HINDSIGHT_PERF_DEFAULTS_UNGATED = [
|
|
|
21237
21243
|
"HINDSIGHT_API_LINK_EXPANSION_TIMEOUT",
|
|
21238
21244
|
String(HINDSIGHT_DEFAULT_LINK_EXPANSION_TIMEOUT_S)
|
|
21239
21245
|
],
|
|
21240
|
-
["HINDSIGHT_API_LLM_REASONING_EFFORT", HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT]
|
|
21246
|
+
["HINDSIGHT_API_LLM_REASONING_EFFORT", HINDSIGHT_DEFAULT_LLM_REASONING_EFFORT],
|
|
21247
|
+
[
|
|
21248
|
+
"HINDSIGHT_API_CONSOLIDATION_LLM_PARALLELISM",
|
|
21249
|
+
String(HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_PARALLELISM)
|
|
21250
|
+
]
|
|
21241
21251
|
];
|
|
21242
21252
|
var HINDSIGHT_PERF_DEFAULTS_GPU = [
|
|
21243
|
-
["HINDSIGHT_API_RERANKER_LOCAL_FP16", HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16]
|
|
21253
|
+
["HINDSIGHT_API_RERANKER_LOCAL_FP16", HINDSIGHT_DEFAULT_RERANKER_LOCAL_FP16],
|
|
21254
|
+
[
|
|
21255
|
+
"HINDSIGHT_API_RERANKER_LOCAL_BATCH_SIZE",
|
|
21256
|
+
String(HINDSIGHT_DEFAULT_RERANKER_LOCAL_BATCH_SIZE)
|
|
21257
|
+
]
|
|
21244
21258
|
];
|
|
21245
21259
|
var HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM = [
|
|
21246
21260
|
["HINDSIGHT_API_LLM_MAX_CONCURRENT", String(HINDSIGHT_DEFAULT_LLM_MAX_CONCURRENT)],
|
|
@@ -21251,13 +21265,21 @@ var HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM = [
|
|
|
21251
21265
|
[
|
|
21252
21266
|
"HINDSIGHT_API_CONSOLIDATION_LLM_MAX_CONCURRENT",
|
|
21253
21267
|
String(HINDSIGHT_DEFAULT_CONSOLIDATION_LLM_MAX_CONCURRENT)
|
|
21254
|
-
]
|
|
21268
|
+
],
|
|
21269
|
+
["HINDSIGHT_API_LLM_STRICT_SCHEMA", HINDSIGHT_DEFAULT_LLM_STRICT_SCHEMA],
|
|
21270
|
+
["HINDSIGHT_API_LLM_MAX_RETRIES", String(HINDSIGHT_DEFAULT_LLM_MAX_RETRIES)]
|
|
21255
21271
|
];
|
|
21272
|
+
var HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS = new Set([
|
|
21273
|
+
"HINDSIGHT_API_WORKER_CONSOLIDATION_BANK_PRIORITY"
|
|
21274
|
+
]);
|
|
21256
21275
|
var HINDSIGHT_PERF_ENV_KEYS = new Set([
|
|
21257
|
-
...
|
|
21258
|
-
|
|
21259
|
-
|
|
21260
|
-
|
|
21276
|
+
...[
|
|
21277
|
+
...HINDSIGHT_PERF_DEFAULTS_UNGATED,
|
|
21278
|
+
...HINDSIGHT_PERF_DEFAULTS_GPU,
|
|
21279
|
+
...HINDSIGHT_PERF_DEFAULTS_LOCAL_LLM
|
|
21280
|
+
].map(([k]) => k),
|
|
21281
|
+
...HINDSIGHT_PERF_OVERRIDE_ONLY_KEYS
|
|
21282
|
+
]);
|
|
21261
21283
|
|
|
21262
21284
|
// src/setup/hindsight-pg-defaults.ts
|
|
21263
21285
|
var HINDSIGHT_PG_MEM_LIMIT_MIB_FOR_DERIVATION = 8 * 1024;
|
|
@@ -21280,6 +21302,10 @@ var HINDSIGHT_PG_DEFAULTS = [
|
|
|
21280
21302
|
];
|
|
21281
21303
|
var HINDSIGHT_PG_ENV_KEYS = new Set(HINDSIGHT_PG_DEFAULTS.map(([k]) => k));
|
|
21282
21304
|
|
|
21305
|
+
// src/setup/hindsight-context-budget.ts
|
|
21306
|
+
var HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE = 3000;
|
|
21307
|
+
var HINDSIGHT_RETAIN_MAX_COMPLETION_FLOOR = HINDSIGHT_UPSTREAM_RETAIN_CHUNK_SIZE + 72;
|
|
21308
|
+
|
|
21283
21309
|
// src/setup/hindsight.ts
|
|
21284
21310
|
var HINDSIGHT_DEFAULT_API_PORT = 18888;
|
|
21285
21311
|
var HINDSIGHT_DEFAULT_MCP_URL = `http://127.0.0.1:${HINDSIGHT_DEFAULT_API_PORT}/mcp/`;
|