In the chat-completions stream path, decodeChatCompletionSseData validates each SSE chunk with Schema.is(ChatCompletionChunk) and returns undefined — discarding the entire chunk — on any mismatch, with no error or log.
Because validation is all-or-nothing per chunk, a single unexpected field anywhere in a chunk silently drops everything in it, including streamed tool_calls argument deltas. Provider quirks therefore surface as silently missing content rather than a diagnosable failure.
Concrete instance: Fireworks sends function.name: null on tool-call continuation fragments, which failed the (non-nullable) name schema and dropped every argument delta. That specific case is fixed narrowly in Effect-TS/effect-smol#2338, but the underlying fail-soft-silently behavior remains and the next provider quirk will fail the same invisible way.
Question for maintainers: should the decoder be more lenient about unrecognized/extra fields, or at minimum surface dropped chunks (debug log / error) instead of discarding them silently? Happy to send a follow-up PR once there's a preferred direction.
In the chat-completions stream path,
decodeChatCompletionSseDatavalidates each SSE chunk withSchema.is(ChatCompletionChunk)and returnsundefined— discarding the entire chunk — on any mismatch, with no error or log.Because validation is all-or-nothing per chunk, a single unexpected field anywhere in a chunk silently drops everything in it, including streamed
tool_callsargument deltas. Provider quirks therefore surface as silently missing content rather than a diagnosable failure.Concrete instance: Fireworks sends
function.name: nullon tool-call continuation fragments, which failed the (non-nullable)nameschema and dropped every argument delta. That specific case is fixed narrowly in Effect-TS/effect-smol#2338, but the underlying fail-soft-silently behavior remains and the next provider quirk will fail the same invisible way.Question for maintainers: should the decoder be more lenient about unrecognized/extra fields, or at minimum surface dropped chunks (debug log / error) instead of discarding them silently? Happy to send a follow-up PR once there's a preferred direction.