Summary
When SkillClaw proxies DeepSeek v4 reasoning models (deepseek-v4-flash / deepseek-v4-pro via the opencode.ai / zen/go upstream), the response arrives with content: "" and the actual answer stuffed into the non-standard reasoning_content field. Clients that read only content (e.g. Hermes agent) receive empty output and treat the call as a blank/failed completion.
This is not a silent degradation — every request through the proxy pays an extra round-trip and returns zero usable output; the client's fallback chain then re-issues the request to a direct provider, roughly doubling effective latency and cost.
Reproduction
Direct call to upstream (works, 1.5s, content populated):
POST https://opencode.ai/zen/go/v1/chat/completions
model: deepseek-v4-flash
-> content: "UPSTREAM" (non-empty)
Same call through the SkillClaw proxy (200 OK but empty content):
POST http://127.0.0.1:30000/v1/chat/completions
model: deepseek-v4-flash
-> 200 OK
message.content: ""
message.reasoning_content: "The user wants me to" <- actual output here
finish_reason: "length"
Root cause
skillclaw/api_server.py _handle_request() reads assistant_msg.get("content") but never checks reasoning_content. DeepSeek reasoning models return the visible output in reasoning_content with an empty content field.
Suggested fix
raw_content = assistant_msg.get("content")
# DeepSeek reasoning models return content in reasoning_content instead of content
reasoning_content = assistant_msg.get("reasoning_content") or ""
if not raw_content and reasoning_content:
raw_content = reasoning_content
Environment
- SkillClaw main (as of 2026-08-04)
- Upstream: opencode.ai /zen/go/v1, model deepseek-v4-flash and deepseek-v4-pro
- Hermes agent as the proxied client
We have removed SkillClaw from our stack pending these fixes (see also #52 for the event-loop freeze). Happy to provide more logs or test a patch.
Summary
When SkillClaw proxies DeepSeek v4 reasoning models (deepseek-v4-flash / deepseek-v4-pro via the opencode.ai / zen/go upstream), the response arrives with
content: ""and the actual answer stuffed into the non-standardreasoning_contentfield. Clients that read onlycontent(e.g. Hermes agent) receive empty output and treat the call as a blank/failed completion.This is not a silent degradation — every request through the proxy pays an extra round-trip and returns zero usable output; the client's fallback chain then re-issues the request to a direct provider, roughly doubling effective latency and cost.
Reproduction
Direct call to upstream (works, 1.5s, content populated):
Same call through the SkillClaw proxy (200 OK but empty content):
Root cause
skillclaw/api_server.py_handle_request()readsassistant_msg.get("content")but never checksreasoning_content. DeepSeek reasoning models return the visible output inreasoning_contentwith an emptycontentfield.Suggested fix
Environment
We have removed SkillClaw from our stack pending these fixes (see also #52 for the event-loop freeze). Happy to provide more logs or test a patch.