Add support for claude-haiku-4-5 (#11434)

This commit is contained in:
Ryan H. Tran 2025-10-20 12:56:40 +00:00 committed by GitHub
parent cc18a18874
commit fab64a51b7
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
7 changed files with 36 additions and 16 deletions

View File

@ -116,8 +116,10 @@ const openHandsHandlers = [
"anthropic/claude-3.5",
"anthropic/claude-sonnet-4-20250514",
"anthropic/claude-sonnet-4-5-20250929",
"anthropic/claude-haiku-4-5-20251001",
"openhands/claude-sonnet-4-20250514",
"openhands/claude-sonnet-4-5-20250929",
"openhands/claude-haiku-4-5-20251001",
"sambanova/Meta-Llama-3.1-8B-Instruct",
]),
),

View File

@ -16,6 +16,7 @@ export const VERIFIED_MODELS = [
"claude-3-7-sonnet-20250219",
"claude-sonnet-4-20250514",
"claude-sonnet-4-5-20250929",
"claude-haiku-4-5-20251001",
"claude-opus-4-20250514",
"claude-opus-4-1-20250805",
"gemini-2.5-pro",
@ -55,6 +56,7 @@ export const VERIFIED_ANTHROPIC_MODELS = [
"claude-3-7-sonnet-20250219",
"claude-sonnet-4-20250514",
"claude-sonnet-4-5-20250929",
"claude-haiku-4-5-20251001",
"claude-opus-4-20250514",
"claude-opus-4-1-20250805",
];
@ -72,6 +74,7 @@ export const VERIFIED_MISTRAL_MODELS = [
export const VERIFIED_OPENHANDS_MODELS = [
"claude-sonnet-4-20250514",
"claude-sonnet-4-5-20250929",
"claude-haiku-4-5-20251001",
"gpt-5-2025-08-07",
"gpt-5-mini-2025-08-07",
"claude-opus-4-20250514",

View File

@ -100,5 +100,5 @@ disallow_untyped_defs = true
ignore_missing_imports = true
[tool.uv.sources]
openhands-sdk = { git = "https://github.com/All-Hands-AI/agent-sdk.git", subdirectory = "openhands/sdk", rev = "50b094a92817e448ec4352d2950df4f19edd5a9f" }
openhands-tools = { git = "https://github.com/All-Hands-AI/agent-sdk.git", subdirectory = "openhands/tools", rev = "50b094a92817e448ec4352d2950df4f19edd5a9f" }
openhands-sdk = { git = "https://github.com/All-Hands-AI/agent-sdk.git", subdirectory = "openhands/sdk", rev = "4ffaa97a9a438b913b73696e192b5575419407bc" }
openhands-tools = { git = "https://github.com/All-Hands-AI/agent-sdk.git", subdirectory = "openhands/tools", rev = "4ffaa97a9a438b913b73696e192b5575419407bc" }

18
openhands-cli/uv.lock generated
View File

@ -1281,7 +1281,7 @@ wheels = [
[[package]]
name = "litellm"
version = "1.77.7"
source = { git = "https://github.com/BerriAI/litellm.git?rev=v1.77.7.dev9#763d2f8ccdd8412dbe6d4ac0e136d9ac34dcd4c0" }
source = { registry = "https://pypi.org/simple" }
dependencies = [
{ name = "aiohttp" },
{ name = "click" },
@ -1296,6 +1296,10 @@ dependencies = [
{ name = "tiktoken" },
{ name = "tokenizers" },
]
sdist = { url = "https://files.pythonhosted.org/packages/5a/4b/4e9a204462687ca3796cc0fdaefbd624d7b2216edd4ad243d60a3b95127e/litellm-1.77.7.tar.gz", hash = "sha256:e3398fb2575b98726e787c0a1481daed5938d58cafdcd96fbca80c312221af3e", size = 10401706, upload-time = "2025-10-05T00:22:37.646Z" }
wheels = [
{ url = "https://files.pythonhosted.org/packages/86/50/53df2244d4aca2af73d2f2c6ad21c731cf24bd0dbe89d896184a1eaa874f/litellm-1.77.7-py3-none-any.whl", hash = "sha256:1b3a1b17bd521a0ad25226fb62a912602c803922aabb4a16adf83834673be574", size = 9223061, upload-time = "2025-10-05T00:22:34.112Z" },
]
[[package]]
name = "macholib"
@ -1652,8 +1656,8 @@ dev = [
[package.metadata]
requires-dist = [
{ name = "openhands-sdk", git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Fsdk&rev=50b094a92817e448ec4352d2950df4f19edd5a9f" },
{ name = "openhands-tools", git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Ftools&rev=50b094a92817e448ec4352d2950df4f19edd5a9f" },
{ name = "openhands-sdk", git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Fsdk&rev=4ffaa97a9a438b913b73696e192b5575419407bc" },
{ name = "openhands-tools", git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Ftools&rev=4ffaa97a9a438b913b73696e192b5575419407bc" },
{ name = "prompt-toolkit", specifier = ">=3" },
{ name = "typer", specifier = ">=0.17.4" },
]
@ -1676,8 +1680,8 @@ dev = [
[[package]]
name = "openhands-sdk"
version = "1.0.0"
source = { git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Fsdk&rev=50b094a92817e448ec4352d2950df4f19edd5a9f#50b094a92817e448ec4352d2950df4f19edd5a9f" }
version = "1.0.0a1"
source = { git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Fsdk&rev=4ffaa97a9a438b913b73696e192b5575419407bc#4ffaa97a9a438b913b73696e192b5575419407bc" }
dependencies = [
{ name = "fastmcp" },
{ name = "httpx" },
@ -1691,8 +1695,8 @@ dependencies = [
[[package]]
name = "openhands-tools"
version = "1.0.0"
source = { git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Ftools&rev=50b094a92817e448ec4352d2950df4f19edd5a9f#50b094a92817e448ec4352d2950df4f19edd5a9f" }
version = "1.0.0a1"
source = { git = "https://github.com/All-Hands-AI/agent-sdk.git?subdirectory=openhands%2Ftools&rev=4ffaa97a9a438b913b73696e192b5575419407bc#4ffaa97a9a438b913b73696e192b5575419407bc" }
dependencies = [
{ name = "bashlex" },
{ name = "binaryornot" },

View File

@ -166,6 +166,7 @@ VERIFIED_OPENAI_MODELS = [
VERIFIED_ANTHROPIC_MODELS = [
'claude-sonnet-4-20250514',
'claude-sonnet-4-5-20250929',
'claude-haiku-4-5-20251001',
'claude-opus-4-20250514',
'claude-opus-4-1-20250805',
'claude-3-7-sonnet-20250219',
@ -188,6 +189,7 @@ VERIFIED_MISTRAL_MODELS = [
VERIFIED_OPENHANDS_MODELS = [
'claude-sonnet-4-20250514',
'claude-sonnet-4-5-20250929',
'claude-haiku-4-5-20251001',
'gpt-5-2025-08-07',
'gpt-5-mini-2025-08-07',
'claude-opus-4-20250514',

View File

@ -148,10 +148,12 @@ class LLM(RetryMixin, DebugMixin):
logger.debug(
f'Gemini model {self.config.model} with reasoning_effort {self.config.reasoning_effort} mapped to thinking {kwargs.get("thinking")}'
)
elif 'claude-sonnet-4-5' in self.config.model:
kwargs.pop(
'reasoning_effort', None
) # don't send reasoning_effort to Claude Sonnet 4.5
elif any(
k in self.config.model
for k in ('claude-sonnet-4-5', 'claude-haiku-4-5-20251001')
):
# don't send reasoning_effort to specific Claude Sonnet/Haiku 4.5 variants
kwargs.pop('reasoning_effort', None)
else:
kwargs['reasoning_effort'] = self.config.reasoning_effort
kwargs.pop(
@ -511,6 +513,7 @@ class LLM(RetryMixin, DebugMixin):
'claude-3.7-sonnet',
'claude-sonnet-4',
'claude-sonnet-4-5-20250929',
'claude-haiku-4-5-20251001',
]
if any(model in self.config.model for model in sonnet_models):
self.config.max_output_tokens = 64000 # litellm set max to 128k, but that requires a header to be set
@ -819,9 +822,14 @@ class LLM(RetryMixin, DebugMixin):
message.force_string_serializer = True
if 'kimi-k2-instruct' in self.config.model and 'groq' in self.config.model:
message.force_string_serializer = True
if 'openrouter/anthropic/claude-sonnet-4' in self.config.model:
message.force_string_serializer = True
if 'openrouter/anthropic/claude-sonnet-4-5-20250929' in self.config.model:
if any(
k in self.config.model
for k in (
'openrouter/anthropic/claude-sonnet-4',
'openrouter/anthropic/claude-sonnet-4-5-20250929',
'openrouter/anthropic/claude-haiku-4-5-20251001',
)
):
message.force_string_serializer = True
# let pydantic handle the serialization

View File

@ -104,6 +104,7 @@ REASONING_EFFORT_PATTERNS: list[str] = [
# DeepSeek reasoning family
'deepseek-r1-0528*',
'claude-sonnet-4-5*',
'claude-haiku-4-5*',
]
PROMPT_CACHE_PATTERNS: list[str] = [