Repository navigation
Replies: 1 comment
|
Second independent occurrence: 0.2.1-rc.2 + QQ chat bridge + billion-context — same 400, plus evidence it is not deterministic Environment:
What happened:
(request_id Points that corroborate / extend your findings:
Recovery matched yours: the session is bricked (the poisoned history persists); opening a new chat was the only fix. The auto-fallback to another provider did restore service, consistent with your Happy to provide the turn-9 session event dump if useful. |
0 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Summary
On
@deepseek-ai/dsh@0.2.1-rc.2(npx, Windows,dsh web), a session that usesdeepseek-official/deepseek-flash(which declarestoolUpdate: "addition-only") starts returning HTTP 400 for every subsequent turn after the tool set changes once mid-conversation:The failure is not transient: the offending mid-conversation tool change stays in the session history and every later turn is rejected the same way, so the session is permanently unusable. Restarting the harness does not help (the history is on disk).
Environment
@deepseek-ai/dsh@0.2.1-rc.2, run vianpx,dsh webon Windows 11deepseek-official, modeldeepseek-flash(contextWindow: 1e6,systemPromptUpdate: "in-history",toolUpdate: "addition-only")@zaofan/dsh-qqbot), i.e. turns are driven by an external plugin, not by the Web UI; the agent preset is a custom oneacp_cache,acp_read_original_image,acp_status,compress,decompress,search_contextTimeline from the session event log
session.v4.jsonl.zstd(workspace session dir~/.dsh/sessions/--...--/<session-id>/) contains, for the failing session:system/message, then 6 ×user/message,request/header(tools start with the preset tools),assistant/message— OKstep/start, 3 ×user/message,request/header, then adeveloper/message:{"type":"developer/message","seq":29,"headerSeq":28,"surfaceOp":"append", "message":{"source":{"kind":"tool-registry"}, "content":[{"type":"tool-addition","toolName":"acp_cache"}, {"type":"tool-addition","toolName":"acp_read_original_image"}, {"type":"tool-addition","toolName":"acp_status"}, {"type":"tool-addition","toolName":"compress"}, {"type":"tool-addition","toolName":"decompress"}, {"type":"tool-addition","toolName":"search_context"}]}}and immediately
assistant/attemptfails, thenstep/end/turn/endrecord the same 400.developer/messageand no newrequest/header— the failure replays the same poisoned history, indexmessages.2is stable.Where the error points
messages.2is the 0-based index in the requestmessagesarray. Direct probes againsthttps://api.deepseek.com/anthropic/messages(anthropic-version: 2023-06-01,anthropic-beta: mid-conversation-tool-changes-2026-07-01, all 6 tool names pre-declared intools):messages[user, assistant, user, {role:"system", content:[tool_addition(tool_reference)×6]}][user, assistant, {role:"system", …}, user][user, assistant, {role:"user", content:[text, tool_addition×6]}]messages.2: tool_addition blocks can only be in system messages(byte-identical to the production error)tool_additionwithtool:{type:"tool_definition", …}unknown variant tool_definition, expected tool_referencetool_additionreferencing a name absent fromtoolsmessages.3.content.0: tool_addition references unknown tool 'acp_cache'So the server side is behaving as intended: an in-array
systemmessage carryingtool_addition/tool_referenceis accepted (with or without the beta header), while the same block inside a non-systemmessage is rejected at that message's index. The production request therefore had the addition blocks inside a non-systemmessages[2].What I could not reproduce
Instantiating the exported
DeepSeekAdapter(@deepseek-ai/dsh-llm-deepseek) with a local HTTP sink and reconstructing the history from the event log ([system, user×6, assistant, user×3, developer]) always yields:{"messages":[ {"role":"user","content":[ …6 user messages merged… ]}, {"role":"assistant","content":[…]}, {"role":"user","content":[ …3 user messages merged… ]}, {"role":"system","content":[ tool_addition×6 ]} ]}i.e. the additions end up in a separate
systemmessage at index 3, which the API accepts. Feeding the same blocks in wire form (tool_addition) inside a user message is rejected locally withUNSUPPORTED_CONTENT: DeepSeek Messages cannot represent user/tool-result content tool_addition, so the serializer never emits that shape. I also checked that nothing on this install rewrites the request: onlydsh-llm-deepseek-api-keyregisters providerdeepseek-official, the onlydeepseekLlmApiExtensionsregistrants write the fieldsdsh_session_loganddsh_plugin_packages, and the profile plugins (chat plugin, compaction plugin) contain notool_additionhandling.So the corrupted shape appears somewhere I could not identify, between session projection and the bytes on the wire. One asymmetry worth a look: the durable-block guard in
dsh-llm-deepseek(lib/index.js, non-developer message branch,~:1661) only matches the hyphenated durable namestool-addition/tool-removal, so a wire-shapedtool_additionblock sitting in a non-developer message would not hit that guard.Recovery / workaround (for other users hitting this)
toolUpdate(e.g.deepseek-v4-pro) or dropping the session (new chat / clear the binding) gets you out.Questions
toolUpdate: "addition-only"+ tools registered after the first turn) or a bug we should dig into further?developer/messagebricks the session.Happy to provide the full
session.v4.jsonlevent dump, the captured request bodies, and the probe scripts if useful.All reactions