/** * Capability-aware parameters for every model call the generation engine makes. * * WHAT BROKE. The Claude 5 line (and Opus 4.7/4.8 before it) REMOVED the * sampling parameters. A request carrying `temperature`, `top_p`, or `top_k` * is rejected outright: * * 400 invalid_request_error — "`temperature` is deprecated for this model." * * (verified live against api.anthropic.com on 2026-07-26: `claude-opus-5` + * `temperature: 0` → 400, the same request without it → 200, and * `claude-sonnet-4-6` + `temperature: 0` → 200). The engine hardcoded * `temperature: 0` at every model call, so a host that configured any Claude 5 * model could not generate AT ALL — every create, edit, repair, and verify * pass failed on the first request. * * The same id split drives a second, quieter failure. `@ai-sdk/anthropic` is a * HOST-supplied peer, not something this package pins for the host: a provider * whose model registry predates the 5 line treats those ids as unknown and * silently defaults `max_tokens` to 4096, truncating generated wire mid-app * with no error and no warning. A silently truncated app is worse than a loud * failure, and it has exactly the same trigger as the sampling rejection (an id * the sampling-era registry does not know), so both fixes travel together here. * * WHY MODEL-ID MATCHING, and not the alternatives: * * - try-and-fallback on the 400 would burn a wasted round trip on every * first call, and the engine's main path is `streamText`, which does NOT * throw provider errors — the rejection arrives as a silently empty text * stream, so there is nothing dependable to catch. It would also make the * test suite depend on live provider behaviour. * - explicit host configuration would leave every existing host broken by * default, and force each one to learn a new knob just to restate a fact * about the model that we already know. * - id matching is deterministic, needs no configuration, costs no round * trip, and is unit-testable offline. Its one risk is an id we do not * recognise, which the rule below resolves in the safe direction. * * THE RULE (this is where it lives): sampling support is an ALLOWLIST of the * Claude families that predate the removal. Anthropic only ever moves ids INTO * the rejecting set, so an unrecognised `claude-*` id is treated as rejecting. * Guessing "rejects" on a model that actually accepts costs determinism we were * never promised — `temperature: 0` has never guaranteed identical output — * while guessing "accepts" on a model that rejects is a hard 400 and a total * generation outage. Non-Claude models are left completely untouched: every * other provider still takes sampling, and this must not regress them. */ import type { LanguageModel } from "ai"; /** * Output cap applied to models whose ids a sampling-era provider registry does * not recognise. It has to clear the provider's silent 4096 default by enough * to hold adaptive thinking plus a full generated app document — thinking is on * by default across the Claude 5 line and `max_tokens` caps thinking and * response text together. * * 64K, not 128K: this is a ceiling rather than an allocation, so an unreached * cap costs nothing, but a cap ABOVE the model's true limit is itself a 400. * 128K is the Claude 5 ceiling, while the Haiku tier caps at 64K — so 64K is * the largest value that stays valid for a small-output model we have not seen * yet, which is precisely the case this constant exists to cover. */ export declare const UNKNOWN_MODEL_MAX_OUTPUT_TOKENS = 64000; /** Whether this model accepts `temperature` / `top_p` / `top_k`. Non-Claude * models always do; Claude models do only on the pre-removal families; the * vendo Cloud gateway family maps to the Claude 5 line server-side, so it * rejects (and needs the explicit output cap above all). */ export declare const acceptsSamplingParams: (model: LanguageModel) => boolean; /** Parameters to spread into a `generateText` / `streamText` call. */ export interface ModelCallParams { temperature?: number; maxOutputTokens?: number; } /** * The engine's OWN determinism default for a model call. Spread this into * every `generateText` / `streamText` call generation makes. * * On a model that takes sampling this is exactly today's behaviour — * `temperature: 0`, no output cap, so currently-supported models are not * regressed in any way. On a model that rejects sampling the temperature is * dropped (it is the engine's own preference, not a caller's instruction) and * an explicit output cap is set so an unaware provider cannot silently fall * back to 4096. */ export declare const modelCallParams: (model: LanguageModel) => ModelCallParams; //# sourceMappingURL=model-params.d.ts.map