Narrow Anthropic 4.7 sampling-removed gate to Opus only (PR #5711)
The 4.7 generation only shipped Claude Opus 4.7; Sonnet stops at 4.6 and Haiku at 4.5 per https://platform.claude.com/docs/en/about-claude/models/overview. The earlier `^claude-(?:opus|sonnet|haiku)-4-7` regex on both the backend strip (_ANTHROPIC_4_7_SAMPLING_REMOVED in external_provider.py) and the frontend mirror (ANTHROPIC_4_7_SAMPLING_REMOVED_REGEX in provider-capabilities.ts) would have pre-emptively hidden temperature / top_p / top_k for any future claude-sonnet-4-7 or claude-haiku-4-7 id, even though Anthropic has explicitly not extended the sampling removal beyond Opus. Tighten both regexes to `^claude-opus-4-7(?:[-.]|$)` and update the routing-test pin so claude-sonnet-4-7 and claude-haiku-4-7 are in `should_not_match`. If those ids ever ship and adopt the same removal, widening the regex is one-line.
This commit is contained in:
parent
6b300699bf
commit
22111744a4
3 changed files with 28 additions and 21 deletions
|
|
@ -71,14 +71,16 @@ def _normalize_stop_for_provider(
|
|||
return None
|
||||
|
||||
|
||||
# Claude 4.7 (Opus/Sonnet/Haiku) removed temperature, top_p, and top_k —
|
||||
# the API returns 400 "<param> is deprecated for this model" if any of
|
||||
# them is set to a non-default value. The "Sampling parameters removed"
|
||||
# section of the 4.7 release notes is the authoritative reference:
|
||||
# Claude 4.7 Opus removed temperature, top_p, and top_k — the API
|
||||
# returns 400 "<param> is deprecated for this model" if any of them is
|
||||
# set to a non-default value. The "Sampling parameters removed" section
|
||||
# of the 4.7 release notes is the authoritative reference:
|
||||
# https://platform.claude.com/docs/en/about-claude/models/whats-new-claude-4-7
|
||||
# 3.x and 4.5/4.6 still accept all three; match the 4-7 line strictly so
|
||||
# the knobs keep working on earlier families. The trailing -4-7[-.]/EOL
|
||||
# anchor keeps future versions (e.g. claude-opus-5) unaffected.
|
||||
# Only Opus shipped in the 4.7 generation (Sonnet stops at 4.6, Haiku at
|
||||
# 4.5 per https://platform.claude.com/docs/en/about-claude/models/overview),
|
||||
# so the regex is anchored to opus-4-7 only. 3.x and 4.5/4.6 still accept
|
||||
# all three knobs; the trailing -4-7[-.]/EOL anchor keeps future versions
|
||||
# (e.g. claude-opus-5) unaffected.
|
||||
def _is_openai_family_cloud(base_url: Optional[str]) -> bool:
|
||||
"""True iff ``base_url`` points at OpenAI cloud or Azure OpenAI Foundry.
|
||||
|
||||
|
|
@ -107,9 +109,7 @@ def _is_openai_family_cloud(base_url: Optional[str]) -> bool:
|
|||
return host == "api.openai.com" or host.endswith(".openai.azure.com")
|
||||
|
||||
|
||||
_ANTHROPIC_4_7_SAMPLING_REMOVED = re.compile(
|
||||
r"^claude-(?:opus|sonnet|haiku)-4-7(?:[-.]|$)"
|
||||
)
|
||||
_ANTHROPIC_4_7_SAMPLING_REMOVED = re.compile(r"^claude-opus-4-7(?:[-.]|$)")
|
||||
_OPENAI_REASONING_SUMMARY_UNSUPPORTED = re.compile(r"^o3(?:[-.]|$)")
|
||||
_OPENAI_REASONING_STATUSES = {"in_progress", "completed", "incomplete"}
|
||||
|
||||
|
|
|
|||
|
|
@ -1105,14 +1105,18 @@ def test_anthropic_4_7_sampling_removed_regex_matches_expected_ids():
|
|||
_ANTHROPIC_4_7_SAMPLING_REMOVED as RX,
|
||||
)
|
||||
|
||||
# Only Opus shipped in the 4.7 generation per
|
||||
# platform.claude.com/docs/en/about-claude/models/overview; Sonnet
|
||||
# stops at 4.6 and Haiku at 4.5. Pin both directions explicitly so
|
||||
# the regex never widens by accident.
|
||||
should_match = [
|
||||
"claude-opus-4-7",
|
||||
"claude-sonnet-4-7",
|
||||
"claude-haiku-4-7",
|
||||
"claude-opus-4-7-20260418",
|
||||
"claude-sonnet-4-7.1",
|
||||
"claude-opus-4-7.1",
|
||||
]
|
||||
should_not_match = [
|
||||
"claude-sonnet-4-7",
|
||||
"claude-haiku-4-7",
|
||||
"claude-opus-4-6",
|
||||
"claude-sonnet-4-6",
|
||||
"claude-haiku-4-5",
|
||||
|
|
|
|||
|
|
@ -686,12 +686,14 @@ function isOpenAIReasoningModelId(modelId: string | null | undefined): boolean {
|
|||
}
|
||||
|
||||
// Mirror of backend _ANTHROPIC_4_7_SAMPLING_REMOVED in
|
||||
// studio/backend/core/inference/external_provider.py:110. Claude 4.7
|
||||
// (Opus/Sonnet/Haiku) removed temperature, top_p, and top_k entirely;
|
||||
// surfacing the sliders would let the user move a control that the
|
||||
// backend silently strips. The trailing -4-7[-.]/EOL anchor keeps future
|
||||
// families (claude-opus-5 etc.) unaffected.
|
||||
const ANTHROPIC_4_7_SAMPLING_REMOVED_REGEX = /^claude-(?:opus|sonnet|haiku)-4-7(?:[-.]|$)/i;
|
||||
// studio/backend/core/inference/external_provider.py:110. Claude Opus
|
||||
// 4.7 removed temperature, top_p, and top_k entirely; surfacing the
|
||||
// sliders would let the user move a control that the backend silently
|
||||
// strips. Only Opus shipped in the 4.7 generation (Sonnet stops at 4.6,
|
||||
// Haiku at 4.5 per platform.claude.com/docs/en/about-claude/models/
|
||||
// overview), so the regex is opus-only. The trailing -4-7[-.]/EOL
|
||||
// anchor keeps future families (claude-opus-5 etc.) unaffected.
|
||||
const ANTHROPIC_4_7_SAMPLING_REMOVED_REGEX = /^claude-opus-4-7(?:[-.]|$)/i;
|
||||
|
||||
function isClaude47SamplingRemoved(modelId: string | null | undefined): boolean {
|
||||
const normalized = modelId?.trim().toLowerCase() ?? "";
|
||||
|
|
@ -849,8 +851,9 @@ const DEFAULT_EXTERNAL_CAPABILITIES = OPENAI_COMPAT_BASE;
|
|||
* gpt-3.5-turbo): full sampling surface (OPENAI_CHAT_CAPABILITIES).
|
||||
* - openai + reasoning model (gpt-5.x, o1, o3, o4): restrictive
|
||||
* (OPENAI_REASONING_CAPABILITIES).
|
||||
* - anthropic + claude-*-4-7: temperature/top_p/top_k stripped to
|
||||
* match the backend 400-avoidance regex.
|
||||
* - anthropic + claude-opus-4-7: temperature/top_p/top_k stripped to
|
||||
* match the backend 400-avoidance regex (Sonnet/Haiku 4.7 do not
|
||||
* ship; only Opus does in the 4.7 generation).
|
||||
* - deepseek + reasoning model (deepseek-reasoner / r1): hides
|
||||
* temperature/top_p (silently ignored upstream).
|
||||
*/
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue