Hmbown/CodeWhale · error
Zen Messages request should succeed
Error message
Zen Messages request should succeed
What it means
Test-side `.expect("Zen Messages request should succeed")` panic. `create_message` returned `Err` for a `WireFormat::AnthropicMessages` client hitting the mocked `/v1/messages` endpoint. The non-streaming Anthropic Messages path failed to complete, either before sending (route/auth resolution) or on a non-2xx/unparseable response.
Solutions
- Print the error (`{e:?}`) to distinguish send failure from response-parse failure.
- Verify the mock mounted at `POST /v1/messages` returns the full Anthropic Messages JSON fixture including `usage`.
- Confirm `client.wire_format == WireFormat::AnthropicMessages` (asserted above) so the request targets `/v1/messages`.
- If the client's auth changed, remember Messages uses `x-api-key` + `anthropic-version`, not Bearer.
Example fix
// before
client
.create_message(minimal_zen_request("claude-sonnet-4-6"))
.await
.expect("Zen Messages request should succeed");
// after
client
.create_message(minimal_zen_request("claude-sonnet-4-6"))
.await
.unwrap_or_else(|e| panic!("Zen Messages request should succeed: {e:?}")); Defensive patterns
Strategy: try-catch
Validate before calling
// Rust (preconditions)
assert_eq!(client.wire_format, WireFormat::AnthropicMessages);
// fixture must satisfy the parser:
assert!(fixture.get("usage").is_some() && fixture.get("content").is_some()); Try / catch
match client.create_message(req).await {
Ok(msg) => assert!(!msg.content.is_empty()),
Err(e) => panic!("Messages request should succeed: {e:?}"),
} Prevention
- Keep the Anthropic Messages fixture complete: id, type, role, content, stop_reason, usage.
- Update the response parser and fixtures in the same commit.
- Assert wire_format before the call to catch route misresolution early.
- Remember Messages auth is x-api-key + anthropic-version, not Bearer.
When it happens
Trigger: Running `opencode_zen_messages_request_shape_uses_api_key_anthropic_route` when the mock route path no longer matches (`/v1/messages`), the client resolves a different wire format for claude-sonnet-4-6, or the mocked JSON response no longer satisfies the Messages response parser (missing `content`, `stop_reason`, or `usage` fields).
Common situations: Changing the Anthropic response schema the parser expects; route constants or base_url changes; mock fixture edited so required fields (`id`, `type`, `role`, `content`, `usage`) are missing.
Understand the failure class
Background: 'Something went wrong' / 'Request failed (500)' / 'HTTP error! status: 404' — what failed HTTP requests actually mean and how to find the real cause — this error's family across 28 libraries.
Related errors
- Zen Responses request should start
- Absolute path should not warn
- Anthropic API error (HTTP )
- child assignment
- child-local search
AI-assisted analysis of Hmbown/CodeWhale@73e0f67d83 (2026-09-22).
Data as JSON: /api/errors/0c50052a9f47816d.
Report an issue: GitHub.
Appendix: source
Thrown at crates/tui/src/client.rs:8170
"id": "msg_zen",
"type": "message",
"role": "assistant",
"content": [{"type": "text", "text": "ok"}],
"model": "claude-sonnet-4-6",
"stop_reason": "end_turn",
"stop_sequence": null,
"usage": {"input_tokens": 1, "output_tokens": 1}
})))
.expect(1)
.mount(&server)
.await;
let client = opencode_zen_client(&server, "claude-sonnet-4-6");
assert_eq!(client.wire_format, WireFormat::AnthropicMessages);
client
.create_message(minimal_zen_request("claude-sonnet-4-6"))
.await
.expect("Zen Messages request should succeed");
let requests = server.received_requests().await.expect("recorded request");
assert_eq!(requests.len(), 1);
assert_zen_messages_api_key_without_bearer(&requests[0]);
assert_eq!(
requests[0]
.headers
.get("anthropic-version")
.and_then(|value| value.to_str().ok()),
Some("2023-06-01")
);
}
#[tokio::test]
async fn opencode_zen_chat_request_uses_chat_completions_route() {
let server = MockServer::start().await;
Mock::given(method("POST"))
.and(path("/v1/chat/completions"))View on GitHub (pinned to 73e0f67d83)