import { type Brain, type BreakerState } from "@sema-agent/core"; import type { ServiceConfig } from "./config-types.js"; /** * 配了快切层(failover ≥2 路 / 断路器)时,**每路**的重试上限。 * * 取 2 的理由:留够吸收一次瞬时抖动(2 次递增退避 ≈ 500ms + 1000ms ≈ 1.5s),同时让外层在秒级而不是 * 分钟级拿到错误。断路器阈值 5 在这个值下 ≈ 7.5s 开路 —— 与它"快速失败让 failover 立刻切备"的设计意图 * 同量级。详见 createBrain 里 retryCap 那段的由来。 */ export declare const FAST_FAIL_MAX_RETRIES = 2; /** * Build the external "Brain" (LLM) from config. * * Composition (A1 + the 1.38 resilience stack, ordered timeout-innermost → breaker → failover-outermost): * - **Tiered timeouts** (1.38, `connectTimeoutMs`/`firstTokenTimeoutMs`) are passed into each * openai-compatible brain at creation — they bound "gateway never accepts the connection" and * "stream opened but hangs without a token" as retryable `[network]` failures. Default ON * (connect 30s per the fleet-audit recommendation; first-token 600s since S-202 — a self-hosted backend's long * prefill legitimately takes minutes to the first byte, and 120s turned that into a retry handing the * same prompt back to the same queue. env =0 disables; env =120000 restores the old posture). * - **Circuit breaker** (`createCircuitBreakerBrain`) wraps the *primary* gateway route(s) when * `MODEL_CIRCUIT_BREAKER=true`: after N transient failures it opens and fast-fails, so failover * switches to the bare backup immediately instead of waiting out each timeout. The last gateway * route stays bare (last-resort) — matching core [ref]. State is core's in-process Map (each * replica trips independently; cross-replica shared state via a TiDB adapter is a follow-up). * - **Failover** (`createFailoverBrain`) stacks the primary gateway with optional * `MODEL_GATEWAY_FALLBACK_URLS` — same protocol, same model id, tried in order. * - **Routing** (`createRoutingBrain`, by `model.provider`) selects the cloud Anthropic Messages * route for `provider:"anthropic"`, and the gateway/failover stack for everything else. (Anthropic * ↔ vLLM is a *routing* choice, not failover.) * * When no fallback URL, no Anthropic key, and no resilience thresholds are configured, this returns the * bare openai brain (carrying the default-on watchdog timeouts — set the three env knobs to 0 for the * pre-[ref] fully-bare shape). The Model itself (id / contextWindow / maxTokens / provider) flows * per-request through `Runner({ models })`. */ export declare function createBrain(config: ServiceConfig, deps?: { fetchImpl?: typeof fetch; breakerState?: BreakerState; }): Brain; /** One-line summary of the active brain composition, for the startup log. */ export declare function brainSummary(config: ServiceConfig): Record; //# sourceMappingURL=brain.d.ts.map