Files
OmniRoute/tests
Andrew B. 2611f5a40b fix(stream): synthesize terminal finish_reason chunk when upstream omits it (#7800) (#7804)
* fix(stream): synthesize terminal finish_reason chunk when upstream omits it (#7800)

Some providers close the SSE stream without emitting a final chunk
carrying a non-null finish_reason. The OpenAI spec requires the terminal
chunk to include finish_reason (e.g. "stop"); strict clients (pi CLI)
reject the stream with "Stream ended without finish_reason".

In passthrough mode (OpenAI Chat Completions shape), track whether a
chunk with non-null finish_reason was seen. If not, synthesize a
terminal chunk with finish_reason "stop" (or "tool_calls" when tool
calls were present) before emitting [DONE].

Translate mode is unaffected — translators (claude-to-openai, gemini-
to-openai) already guarantee a terminal finish_reason chunk via
finishReasonSent / fallback defaults.

Tests: 3 new regression tests covering omission, no-op when upstream
sends finish_reason, and tool_calls variant.

* fix(stream): track finish_reason in flush path to avoid false synthesis (#7800)

The synthetic finish_reason chunk fired even when the upstream DID emit
a finish_reason chunk — but as the final buffered line without a trailing
newline. The flush path (which handles the leftover buffer) normalized
IDs but never set passthroughSawFinishReason, so the synthesis guard
!passthroughSawFinishReason stayed true and emitted a spurious synthetic
chunk with a chatcmpl-* id, breaking the numeric-id normalization test.
2026-07-20 10:08:01 -03:00
..
2026-05-23 01:46:59 -03:00
2026-07-13 09:12:40 -03:00
2026-07-02 10:47:13 -03:00
2026-07-06 02:25:17 -03:00
2026-07-13 09:12:40 -03:00
2026-06-13 17:27:40 -03:00