Skip to content

Luna compatibility policy bypassed by web-search loop forcing upstream streaming #1143

Description

@emanuelmustea

Summary

OpenCodex can successfully work around providers whose Responses/chat streaming is unreliable by setting a per-model upstream-streaming policy to false. However, the web-search loop currently forces stream:true for each internal model iteration, bypassing that policy.

This caused GPT-5.6 Luna through OpenCode Go to keep failing in Codex Desktop even after the provider registry and main Responses normalization paths were configured for buffered upstream requests.

Environment

  • OpenCodex 2.10.2
  • macOS
  • Codex Desktop
  • Provider adapter: openai-chat
  • Provider: OpenCode Go
  • Model: gpt-5.6-luna

Reproduction

  1. Configure a routed model with a provider registry entry such as:
modelResponsesUpstreamStreaming: { "gpt-5.6-luna": false }
  1. Send a Codex Responses request with stream:true, tools, and hosted web_search_preview enabled.
  2. The normal normalization path changes the upstream request to non-streaming.
  3. src/web-search/loop.ts creates an iteration with stream: true and calls the adapter with stream: true.
  4. The provider receives a streaming tool request and fails; OpenCodex returns the truncation error/502.

Without the hosted web-search tool, the buffered compatibility path works. With it, the loop reintroduces upstream streaming.

Expected behavior

The web-search loop should preserve the effective upstream streaming decision for the routed provider/model. A client may still receive downstream SSE synthesized from a completed buffered response, while the upstream request remains non-streaming.

Fix direction

  • Do not unconditionally set iterParsed.stream = true in the web-search loop.
  • Pass the effective stream setting to fetchResponse.
  • Use parseResponse for buffered JSON iterations and parseStream only for genuinely streaming upstream responses.
  • Keep the client-facing web-search loop and SSE behavior unchanged.

This report intentionally excludes API keys, private prompts, and workspace/tool payloads.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    toolstool_calls, MCP, web-search / sidecar tools

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions