import type { LLMProvider, ChatRequest, ChatResponse, ProviderAuthState, ProviderEmbeddingRequest, ProviderEmbeddingResult, ProviderModelSource, ProviderRuntimeMetadata, ProviderRuntimeMetadataDeps } from './interface.js'; import { type LiveModelDiscoveryResult } from './live-model-discovery.js'; import type { ProviderCapability } from './capabilities.js'; import type { CacheHitTracker } from './cache-strategy.js'; /** * Placeholder credential passed to the `openai` package's client constructor * when no real API key is configured (local servers such as Ollama, LM * Studio, llama.cpp, TGI, and LocalAI ignore the value entirely; discovery * registers these providers with `apiKey: ''`). openai's client constructor * has thrown "Missing credentials..." on a falsy `apiKey` (empty string * included) since 6.4x, previously it only threw on `undefined`, so every * unconfigured/anonymous provider broke at registration time once the SDK's * `openai` dependency resolved past that change. This is the SAME literal * already used by the builtin-provider registry's own anonymous fallback * (`packages/sdk/src/platform/providers/builtin-registry.ts`); kept as a * named export so every `new OpenAI(...)` construction site in this codebase * uses one grep-able placeholder. */ export declare const OPENAI_CLIENT_LOCAL_PLACEHOLDER_API_KEY = "gv-local"; /** * Returns an apiKey value safe to pass to `new OpenAI(...)`, substituting the * shared placeholder when the effective key is empty. Callers must derive * `configured`/`isConfigured()` status from the ORIGINAL apiKey (or an * explicit override) BEFORE calling this, never from the substituted value. */ export declare function resolveOpenAIClientApiKey(apiKey: string): string; export interface OpenAICompatOptions { name: string; baseURL: string; apiKey: string; defaultModel: string; models: string[]; embeddingModel?: string | undefined; capabilities?: Partial | undefined; /** Optional extra HTTP headers sent with every request to this provider. */ defaultHeaders?: Record | undefined; /** * Which request field carries reasoning depth. Named for the wire shape, not * the vendor: `reasoning-effort` is the plain OpenAI-compatible * `reasoning_effort` string, `mercury` is the same field plus Mercury-2's * reasoning-summary extras, `openrouter` nests it under `reasoning.effort`, * and `llamacpp` exposes only an `enable_thinking` toggle. Default: 'none' * (send nothing), which is correct for backends that document no control. */ reasoningFormat?: 'mercury' | 'openrouter' | 'llamacpp' | 'reasoning-effort' | 'none' | undefined; /** Optional env vars or secret keys that can satisfy API-key auth for this provider. */ authEnvVars?: readonly string[] | undefined; /** Optional service names that expose service-owned OAuth for this provider. */ serviceNames?: readonly string[] | undefined; /** Optional subscription-provider identity when this provider can use a stored OAuth session. */ subscriptionProviderId?: string | undefined; /** Optional provider-owned model suppression registry keys for runtime metadata consumers. */ suppressedModelRegistryKeys?: readonly string[] | undefined; /** Optional provider aliases exposed to runtime metadata consumers. */ aliases?: readonly string[] | undefined; /** Optional explicit stream protocol label for diagnostics. */ streamProtocol?: string | undefined; /** Optional anonymous/local access posture. */ allowAnonymous?: boolean | undefined; anonymousConfigured?: boolean | undefined; anonymousDetail?: string | undefined; /** Override runtime auth posture when apiKey is an internal transport placeholder. */ authConfigured?: boolean | undefined; /** Shared cache-hit tracker owned by the runtime service graph. */ cacheHitTracker?: Pick | undefined; /** * How this backend's model list is discovered. * - 'openai-endpoint' (default): live discovery from the backend's * OpenAI-style GET {baseURL}/models listing, with `models` demoted to a * dated-static baseline that is used until the first successful fetch * and whenever live discovery fails. * - 'none': the backend has no model-listing API (verified per provider); * `models` is the complete dated-static list and no live fetch is made. */ modelListing?: 'openai-endpoint' | 'none' | undefined; /** Override the model-listing URL (defaults to `${baseURL}/models`). */ modelListingUrl?: string | undefined; /** * Fully custom live-listing fetcher for backends whose listing is not an * OpenAI-style GET (e.g. Fireworks' paginated account-management listing). * Takes precedence over `modelListingUrl`. */ fetchLiveModels?: (() => Promise) | undefined; /** The date the static `models` list was last verified, e.g. '2026-07-12'. */ modelsAsOf?: string | undefined; /** On-disk cache path for live-discovered model lists (TTL cached). */ modelsCachePath?: string | undefined; } /** * OpenAICompatProvider, generic OpenAI-compatible provider. * Configured for InceptionLabs Mercury-2 with reasoning_effort and * reasoning_summary extensions, but usable with any OAI-compatible API. */ export declare class OpenAICompatProvider implements LLMProvider { readonly name: string; readonly credentialAuthority: "resolver"; readonly capabilities?: Partial | undefined; readonly modelSource: ProviderModelSource; /** * Populated synchronously with the configured static list at construction * (never empty), then replaced by `refreshModels()` with the backend's * live listing when `modelListing` is 'openai-endpoint'. See `modelSource`. */ private _models; get models(): string[]; /** * The `openai` client, resolved on first use rather than at construction. * `openai` is an optionalDependency; a static import plus a constructor-time * `new OpenAI(...)` put the specifier on the module graph of every graph * that registers providers, the daemon's included, and an absent optional * package then removed the process instead of one provider. See * utils/optional-dependency.ts. Both methods that use the client already run * inside an async request path, so no public signature changes. */ private openaiClient; private defaultModel; private embeddingModel; private readonly configured; private reasoningFormat; private cacheCapability; private readonly authEnvVars; private readonly serviceNames; private readonly subscriptionProviderId?; private readonly suppressedModelRegistryKeys; private readonly aliases; private readonly streamProtocol?; private readonly allowAnonymous; private readonly anonymousConfigured; private readonly anonymousDetail?; private readonly cacheHitTracker; private readonly baseURL; private readonly endpointHost; private readonly apiKey; private readonly defaultHeaders; /** * The caller's `defaultHeaders` exactly as given, including a deliberate * empty object. `defaultHeaders` above normalises `undefined` to `{}` for * per-request header merging; the client construction below keeps the * original distinction it had when it ran in the constructor. */ private readonly clientDefaultHeaders; private readonly modelListing; private readonly modelListingUrl; private readonly customFetchLiveModels; private readonly datedStaticModels; private readonly modelsAsOf; private readonly modelsCachePath; constructor(opts: OpenAICompatOptions); /** The `openai` client for this provider, built once on first use. */ private client; isConfigured(): boolean; describeAuthState(): ProviderAuthState; /** * No dead-end 401: an unconfigured provider refuses the request BEFORE it * hits the wire, with copy that names the key it needs. A key written to * env/secrets re-registers the provider (credentialAuthority 'resolver'), * so this state is never stale across a key being added. */ private assertConfiguredForChat; /** * Re-check this backend's live model listing. Called at boot (background, * respects the on-disk TTL cache) and on-demand for a picker-open re-check * or an explicit user refresh (`force: true`). Always resolves, falls back * to the on-disk cache, then to the dated-static baseline, and reports the * honest failure reason rather than ever blanking the model list. When the * backend has no listing API (`modelListing: 'none'`, verified per * provider), this reports the dated-static source without a network call. */ refreshModels(force?: boolean): Promise; private fetchLiveModelIds; chat(params: ChatRequest): Promise; embed(request: ProviderEmbeddingRequest): Promise; describeRuntime(deps: ProviderRuntimeMetadataDeps): Promise; } //# sourceMappingURL=openai-compat.d.ts.map