Files
wehub-resource-sync 5296d0e97c
CI / Ban suppressions and legacy annotations (push) Has been cancelled
CI / pytest (push) Has been cancelled
CI / ruff-check (push) Has been cancelled
CI / ruff-format (push) Has been cancelled
CI / ty (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 12:35:44 +08:00

965 lines
32 KiB
Python

from typing import Any
from unittest.mock import MagicMock, patch
import pytest
from fastapi.testclient import TestClient
from free_claude_code.application.errors import InvalidRequestError
from free_claude_code.core.anthropic.stream_contracts import parse_sse_text
from free_claude_code.core.anthropic.streaming import format_sse_event
from free_claude_code.core.failures import ExecutionFailure, FailureKind
from tests.api.support import create_test_app
class FakeProvider:
def __init__(self, chunks: list[str]) -> None:
self.chunks = chunks
self.preflight_stream = MagicMock()
self.requests: list[Any] = []
self.stream_kwargs: list[dict[str, Any]] = []
async def stream_response(self, request_data, **_kwargs):
self.requests.append(request_data)
self.stream_kwargs.append(_kwargs)
for chunk in self.chunks:
yield chunk
class PreStartFailingProvider(FakeProvider):
def __init__(self) -> None:
super().__init__([])
async def stream_response(self, request_data, **_kwargs):
self.requests.append(request_data)
self.stream_kwargs.append(_kwargs)
raise ExecutionFailure(
kind=FailureKind.RATE_LIMIT,
status_code=429,
message="upstream is busy",
retryable=True,
)
yield "unreachable"
class PostStartFailingProvider(FakeProvider):
def __init__(self) -> None:
super().__init__([format_sse_event("message_start", {"type": "message_start"})])
async def stream_response(self, request_data, **_kwargs):
self.requests.append(request_data)
self.stream_kwargs.append(_kwargs)
for chunk in self.chunks:
yield chunk
raise RuntimeError("socket closed")
@pytest.fixture
def responses_client():
provider = FakeProvider(_anthropic_text_stream("Hello from provider"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
yield client, provider
def test_responses_probe_endpoints_return_204(
responses_client: tuple[TestClient, FakeProvider],
) -> None:
client, _provider = responses_client
assert client.head("/v1/responses").status_code == 204
assert client.options("/v1/responses").status_code == 204
def test_create_response_stream_routes_through_provider(
responses_client: tuple[TestClient, FakeProvider],
) -> None:
client, provider = responses_client
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"max_output_tokens": 32,
},
)
assert response.status_code == 200
assert "text/event-stream" in response.headers["content-type"]
assert response.headers["x-request-id"] == response.headers["request-id"]
events = parse_sse_text(response.text)
assert events[0].event == "response.created"
assert events[-1].event == "response.completed"
assert events[-1].data["response"]["output"][0]["content"][0]["text"] == (
"Hello from provider"
)
assert provider.preflight_stream.called
routed = provider.requests[0]
assert routed.model == "test-model"
assert routed.messages[0].role == "user"
assert routed.messages[0].content == "Hello"
assert routed.max_tokens == 32
assert provider.stream_kwargs[0]["request_id"] == response.headers["request-id"]
def test_create_response_preflight_rejection_stays_an_ordinary_http_error() -> None:
provider = FakeProvider(_anthropic_text_stream("unused"))
provider.preflight_stream.side_effect = InvalidRequestError("bad tool shape")
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={"model": "nvidia_nim/test-model", "input": "Hello"},
)
assert response.status_code == 400
assert response.json()["error"] == {
"message": "bad tool shape",
"type": "invalid_request_error",
"param": None,
"code": None,
}
assert "x-should-retry" not in response.headers
assert provider.requests == []
def test_create_response_accepts_unknown_top_level_extensions(
responses_client: tuple[TestClient, FakeProvider],
) -> None:
client, provider = responses_client
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"provider_extension": {"enabled": True},
},
)
assert response.status_code == 200
assert provider.requests[0].messages[0].content == "Hello"
def test_create_response_pre_start_provider_error_returns_openai_error() -> None:
provider = PreStartFailingProvider()
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
patch("free_claude_code.api.response_streams.trace_event") as trace,
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
},
)
assert response.status_code == 429
assert response.headers["x-should-retry"] == "false"
assert response.headers["x-request-id"] == response.headers["request-id"]
payload = response.json()
assert payload["error"]["type"] == "rate_limit_error"
assert payload["error"]["message"] == "upstream is busy"
request_id = response.headers["request-id"]
assert provider.stream_kwargs[0]["request_id"] == request_id
terminal_trace = next(
call.kwargs
for call in trace.call_args_list
if call.kwargs.get("event")
== "free_claude_code.api.response.terminal_execution_error"
)
assert terminal_trace["wire_api"] == "responses"
assert terminal_trace["request_id"] == request_id
assert terminal_trace["status_code"] == 429
assert terminal_trace["error_type"] == "rate_limit_error"
assert terminal_trace["client_should_retry"] is False
assert terminal_trace["failure_kind"] == "rate_limit"
assert terminal_trace["provider_retryable"] is True
def test_create_response_post_start_failure_preserves_response_id() -> None:
provider = PostStartFailingProvider()
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
},
)
assert response.status_code == 200
events = parse_sse_text(response.text)
assert [event.event for event in events] == ["response.created", "response.failed"]
assert events[-1].data["response"]["id"] == events[0].data["response"]["id"]
assert events[-1].data["response"]["status"] == "failed"
assert events[-1].data["response"]["error"]["message"] == "socket closed"
def test_create_response_stream_bypasses_local_message_optimizations() -> None:
provider = FakeProvider(_anthropic_text_stream("Provider response"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
patch(
"free_claude_code.api.handlers.messages.try_optimizations",
side_effect=AssertionError("Responses must not use message optimizations"),
),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "quota check",
},
)
assert response.status_code == 200
completed = parse_sse_text(response.text)[-1].data["response"]
assert completed["output"][0]["content"][0]["text"] == "Provider response"
assert provider.requests[0].messages[0].content == "quota check"
def test_create_response_stream_false_returns_openai_error(
responses_client: tuple[TestClient, FakeProvider],
) -> None:
client, provider = responses_client
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"stream": False,
},
)
assert response.status_code == 400
payload = response.json()
assert payload["error"]["type"] == "invalid_request_error"
assert "streaming only" in payload["error"]["message"]
assert provider.requests == []
def test_create_response_stream_preserves_interleaved_reasoning_order() -> None:
provider = FakeProvider(_anthropic_interleaved_reasoning_stream())
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Use reasoning and tools",
"stream": True,
"tools": [
{
"type": "function",
"name": "echo",
"parameters": {"type": "object", "properties": {}},
}
],
},
)
assert response.status_code == 200
events = parse_sse_text(response.text)
assert "response.reasoning_text.delta" in [event.event for event in events]
completed = events[-1].data["response"]
assert [item["type"] for item in completed["output"]] == [
"reasoning",
"message",
"function_call",
"reasoning",
"message",
]
assert completed["output"][0]["content"][0]["text"] == "first thought"
assert completed["output"][1]["content"][0]["text"] == "first answer"
assert completed["output"][2]["arguments"] == '{"value":"FCC"}'
assert completed["output"][3]["content"][0]["text"] == "second thought"
assert completed["output"][4]["content"][0]["text"] == "final answer"
def test_create_response_tool_stream_emits_function_call() -> None:
provider = FakeProvider(_anthropic_tool_stream())
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Use echo",
"stream": True,
"tools": [
{
"type": "function",
"name": "echo",
"parameters": {"type": "object", "properties": {}},
}
],
},
)
assert response.status_code == 200
events = parse_sse_text(response.text)
completed = events[-1].data["response"]
call = completed["output"][0]
assert call["type"] == "function_call"
assert call["call_id"] == "toolu_1"
assert call["arguments"] == '{"value":"FCC"}'
def test_create_response_malformed_provider_function_call_fails_stream() -> None:
provider = FakeProvider(
_anthropic_tool_stream(partial_json='{"value":"FCC" "bad"}')
)
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Use echo",
"stream": True,
"tools": [
{
"type": "function",
"name": "echo",
"parameters": {"type": "object", "properties": {}},
}
],
},
)
assert response.status_code == 200
events = parse_sse_text(response.text)
assert events[-1].event == "response.failed"
failed = events[-1].data["response"]
assert failed["status"] == "failed"
assert failed["output"] == []
assert "replay-unsafe Responses output" in failed["error"]["message"]
def test_create_response_accepts_codex_namespace_tool_request() -> None:
provider = FakeProvider(_anthropic_tool_stream(tool_name="mcp__node_repl__js"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Use JS",
"stream": True,
"tools": [
{"type": "web_search", "external_web_access": True},
{"type": "image_generation", "output_format": "png"},
{
"type": "namespace",
"name": "mcp__node_repl",
"tools": [
{
"type": "function",
"name": "js",
"parameters": {
"type": "object",
"properties": {"code": {"type": "string"}},
},
}
],
},
],
},
)
assert response.status_code == 200
routed = provider.requests[0]
assert [tool.name for tool in routed.tools] == ["mcp__node_repl__js"]
completed = parse_sse_text(response.text)[-1].data["response"]
call = completed["output"][0]
assert call["namespace"] == "mcp__node_repl"
assert call["name"] == "js"
def test_create_response_accepts_codex_custom_tool_request() -> None:
provider = FakeProvider(
_anthropic_tool_stream(
tool_name="apply_patch",
partial_json='{"input":"*** Begin Patch"}',
)
)
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Use apply_patch",
"stream": True,
"tools": [
{
"type": "custom",
"name": "apply_patch",
"description": "Apply repo patches",
"format": {"type": "text"},
}
],
"tool_choice": {"type": "custom", "name": "apply_patch"},
},
)
assert response.status_code == 200
routed = provider.requests[0]
assert [tool.name for tool in routed.tools] == ["apply_patch"]
assert routed.tool_choice == {"type": "tool", "name": "apply_patch"}
events = parse_sse_text(response.text)
assert "response.custom_tool_call_input.delta" in [event.event for event in events]
completed = events[-1].data["response"]
call = completed["output"][0]
assert call["type"] == "custom_tool_call"
assert call["name"] == "apply_patch"
assert call["input"] == "*** Begin Patch"
def test_create_response_stream_provider_error_returns_response_failed() -> None:
provider = FakeProvider(
[
format_sse_event(
"error",
{
"type": "error",
"error": {
"type": "api_error",
"message": "provider failed",
},
},
)
]
)
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"stream": True,
},
)
assert response.status_code == 200
events = parse_sse_text(response.text)
assert [event.event for event in events] == ["response.created", "response.failed"]
failed = events[-1].data["response"]
assert failed["id"] == events[0].data["response"]["id"]
assert failed["status"] == "failed"
assert failed["error"] == {
"message": "provider failed",
"type": "api_error",
"param": None,
"code": None,
}
def test_create_response_replays_prior_reasoning_as_reasoning_content() -> None:
provider = FakeProvider(_anthropic_text_stream("done"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": [
{
"id": "rs_1",
"type": "reasoning",
"summary": [],
"content": [
{"type": "reasoning_text", "text": "Need the tool."}
],
},
{
"type": "function_call",
"call_id": "call_1",
"name": "echo",
"arguments": "{}",
},
{
"type": "function_call_output",
"call_id": "call_1",
"output": "ok",
},
{
"id": "rs_2",
"type": "reasoning",
"summary": [
{"type": "summary_text", "text": "Use the result."}
],
},
{"role": "user", "content": "continue"},
],
"stream": True,
},
)
assert response.status_code == 200
routed = provider.requests[0]
assert routed.messages[0].role == "assistant"
assert routed.messages[0].reasoning_content == "Need the tool."
assert routed.messages[0].content[0].type == "tool_use"
assert routed.messages[1].role == "user"
assert routed.messages[1].content[0].type == "tool_result"
assert routed.messages[2].role == "assistant"
assert routed.messages[2].content == ""
assert routed.messages[2].reasoning_content == "Use the result."
assert routed.messages[3].role == "user"
assert routed.messages[3].content == "continue"
def test_create_response_quarantines_malformed_prior_function_call() -> None:
provider = FakeProvider(_anthropic_text_stream("done"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": [
{"role": "user", "content": "hello"},
{
"type": "function_call",
"call_id": "call_bad",
"name": "echo",
"arguments": "{",
},
{
"type": "function_call_output",
"call_id": "call_bad",
"output": "stale output",
},
{"role": "user", "content": "continue"},
],
"stream": True,
},
)
assert response.status_code == 200
routed = provider.requests[0]
assert [message.role for message in routed.messages] == ["user", "user"]
assert routed.messages[0].content == "hello"
assert routed.messages[1].content == "continue"
completed = parse_sse_text(response.text)[-1].data["response"]
assert completed["output"][0]["content"][0]["text"] == "done"
@pytest.mark.parametrize(
("reasoning", "expected_type", "expected_enabled"),
[
({"effort": "none"}, "disabled", False),
({"effort": "low"}, "enabled", True),
],
)
def test_create_response_maps_reasoning_effort_to_thinking_request(
reasoning: dict[str, str],
expected_type: str,
expected_enabled: bool,
) -> None:
provider = FakeProvider(_anthropic_text_stream("done"))
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"stream": True,
"reasoning": reasoning,
},
)
assert response.status_code == 200
thinking = provider.requests[0].thinking
assert thinking.type == expected_type
assert thinking.enabled is expected_enabled
def test_create_response_maps_redacted_thinking_to_encrypted_reasoning() -> None:
provider = FakeProvider(_anthropic_redacted_thinking_stream())
app = create_test_app()
with (
patch("free_claude_code.api.routes.resolve_provider", return_value=provider),
TestClient(app) as client,
):
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Continue",
"stream": True,
},
)
assert response.status_code == 200
completed = parse_sse_text(response.text)[-1].data["response"]
assert completed["output"] == [
{
"id": completed["output"][0]["id"],
"type": "reasoning",
"status": "completed",
"summary": [],
"encrypted_content": "opaque-redacted",
}
]
assert "content" not in completed["output"][0]
def test_create_response_unsupported_tool_returns_openai_error(
responses_client: tuple[TestClient, FakeProvider],
) -> None:
client, _provider = responses_client
response = client.post(
"/v1/responses",
json={
"model": "nvidia_nim/test-model",
"input": "Hello",
"tools": [{"type": "web_search_preview"}],
},
)
assert response.status_code == 400
payload = response.json()
assert payload["error"]["type"] == "invalid_request_error"
assert "Unsupported Responses tool type" in payload["error"]["message"]
def _anthropic_text_stream(text: str) -> list[str]:
return [
format_sse_event("message_start", {"type": "message_start", "message": {}}),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 0,
"content_block": {"type": "text", "text": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 0,
"delta": {"type": "text_delta", "text": text},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 0},
),
format_sse_event(
"message_delta",
{
"type": "message_delta",
"delta": {"stop_reason": "end_turn", "stop_sequence": None},
"usage": {"input_tokens": 3, "output_tokens": 4},
},
),
format_sse_event("message_stop", {"type": "message_stop"}),
]
def _anthropic_tool_stream(
tool_name: str = "echo", partial_json: str = '{"value":"FCC"}'
) -> list[str]:
return [
format_sse_event("message_start", {"type": "message_start", "message": {}}),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 0,
"content_block": {
"type": "tool_use",
"id": "toolu_1",
"name": tool_name,
"input": {},
},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 0,
"delta": {
"type": "input_json_delta",
"partial_json": partial_json,
},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 0},
),
format_sse_event(
"message_delta",
{
"type": "message_delta",
"delta": {"stop_reason": "tool_use", "stop_sequence": None},
"usage": {"input_tokens": 3, "output_tokens": 4},
},
),
format_sse_event("message_stop", {"type": "message_stop"}),
]
def _anthropic_reasoning_text_stream() -> list[str]:
return [
format_sse_event("message_start", {"type": "message_start", "message": {}}),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 0,
"content_block": {"type": "thinking", "thinking": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 0,
"delta": {
"type": "thinking_delta",
"thinking": "provider reasoning",
},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 0},
),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 1,
"content_block": {"type": "text", "text": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 1,
"delta": {"type": "text_delta", "text": "provider answer"},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 1},
),
format_sse_event(
"message_delta",
{
"type": "message_delta",
"delta": {"stop_reason": "end_turn", "stop_sequence": None},
"usage": {"input_tokens": 3, "output_tokens": 4},
},
),
format_sse_event("message_stop", {"type": "message_stop"}),
]
def _anthropic_interleaved_reasoning_stream() -> list[str]:
return [
format_sse_event("message_start", {"type": "message_start", "message": {}}),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 0,
"content_block": {"type": "thinking", "thinking": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 0,
"delta": {"type": "thinking_delta", "thinking": "first thought"},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 0},
),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 1,
"content_block": {"type": "text", "text": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 1,
"delta": {"type": "text_delta", "text": "first answer"},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 1},
),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 2,
"content_block": {
"type": "tool_use",
"id": "toolu_1",
"name": "echo",
"input": {},
},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 2,
"delta": {
"type": "input_json_delta",
"partial_json": '{"value":"FCC"}',
},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 2},
),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 3,
"content_block": {"type": "thinking", "thinking": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 3,
"delta": {"type": "thinking_delta", "thinking": "second thought"},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 3},
),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 4,
"content_block": {"type": "text", "text": ""},
},
),
format_sse_event(
"content_block_delta",
{
"type": "content_block_delta",
"index": 4,
"delta": {"type": "text_delta", "text": "final answer"},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 4},
),
format_sse_event(
"message_delta",
{
"type": "message_delta",
"delta": {"stop_reason": "end_turn", "stop_sequence": None},
"usage": {"input_tokens": 3, "output_tokens": 4},
},
),
format_sse_event("message_stop", {"type": "message_stop"}),
]
def _anthropic_redacted_thinking_stream() -> list[str]:
return [
format_sse_event("message_start", {"type": "message_start", "message": {}}),
format_sse_event(
"content_block_start",
{
"type": "content_block_start",
"index": 0,
"content_block": {
"type": "redacted_thinking",
"data": "opaque-redacted",
},
},
),
format_sse_event(
"content_block_stop",
{"type": "content_block_stop", "index": 0},
),
format_sse_event(
"message_delta",
{
"type": "message_delta",
"delta": {"stop_reason": "end_turn", "stop_sequence": None},
"usage": {"input_tokens": 3, "output_tokens": 4},
},
),
format_sse_event("message_stop", {"type": "message_stop"}),
]