fix(deepseek): preserve native reasoning effort for V4 models

This commit is contained in:
BiGy2018 2026-09-22 00:18:10 +08:00
parent aa2219d466
commit c000144685
2 changed files with 48 additions and 0 deletions

View file

@ -59,6 +59,14 @@ class DeepSeekChatConfig(OpenAIGPTConfig):
elif reasoning_effort is not None:
optional_params["thinking"] = {"type": "disabled" if reasoning_effort == "none" else "enabled"}
if (
model.removeprefix("deepseek/").startswith(("deepseek-v4-", "deepseek-flash"))
and optional_params.get("thinking") == {"type": "enabled"}
and isinstance(reasoning_effort, str)
and reasoning_effort != "none"
):
return {**optional_params, "reasoning_effort": reasoning_effort}
return optional_params
def _fill_reasoning_content(self, messages: list[AllMessageValues]) -> list[AllMessageValues]:

View file

@ -1,7 +1,47 @@
from typing import Final
import pytest
import litellm
from litellm.llms.deepseek.chat.transformation import DeepSeekChatConfig
@pytest.mark.parametrize(
"model", ("deepseek-flash", "deepseek-v4-pro", "deepseek-v4-flash-vision-exp", "deepseek/deepseek-v4-flash")
)
@pytest.mark.parametrize("effort", ("minimal", "low", "medium", "high", "xhigh", "max", "ultra"))
@pytest.mark.parametrize("thinking", (None, "enabled"))
def test_v4_keeps_requested_effort_with_enabled_thinking(model: str, effort: str, thinking: str | None) -> None:
params: Final = {"reasoning_effort": effort, **({"thinking": {"type": thinking}} if thinking else {})}
result: Final = DeepSeekChatConfig().map_openai_params(params, {}, model, False)
assert result == {"thinking": {"type": "enabled"}, "reasoning_effort": effort}
@pytest.mark.parametrize(
"thinking,effort,expected",
(
(None, None, {}),
(None, "none", {"thinking": {"type": "disabled"}}),
("disabled", "low", {"thinking": {"type": "disabled"}}),
("disabled", "max", {"thinking": {"type": "disabled"}}),
("enabled", "none", {"thinking": {"type": "enabled"}}),
("enabled", None, {"thinking": {"type": "enabled"}}),
),
)
def test_v4_retains_explicit_thinking_precedence(
thinking: str | None, effort: str | None, expected: dict[str, dict[str, str]]
) -> None:
params: Final = {"reasoning_effort": effort, **({"thinking": {"type": thinking}} if thinking else {})}
result: Final = DeepSeekChatConfig().map_openai_params(params, {}, "deepseek-flash", False)
assert result == expected
@pytest.mark.parametrize("model", ("deepseek-chat", "deepseek-reasoner", "deepseek/deepseek-reasoner"))
def test_legacy_models_retain_toggle_only_mapping(model: str) -> None:
result: Final = DeepSeekChatConfig().map_openai_params({"reasoning_effort": "low"}, {}, model, False)
assert result == {"thinking": {"type": "enabled"}}
def _function_tool(name: str) -> dict:
return {
"type": "function",