Skip to content

Spark canonical Responses streams end with adapter_eof when Responses Lite is enabled #3885

Closed

Description

@cb8010d6

This was generated by AI during triage.

Client or integration

Codex CLI

Area

Provider adapter

Summary

When Codex routes gpt-5.3-codex-spark through the canonical ChatGPT Responses endpoint, forwarding x-openai-internal-codex-responses-lite: true starts an HTTP 200 SSE response but the upstream stream ends before a terminal event. OpenCodex consequently emits response.incomplete with incomplete_details.reason=adapter_eof and records the request as 502.

Replaying the same request after removing only that header completes normally. The expected behavior is for OpenCodex to suppress Responses Lite only for the Spark wire model while preserving existing metadata forwarding for other canonical models.

Reproduction

  1. Use OpenCodex with the canonical OpenAI Codex-login provider and select gpt-5.3-codex-spark.
  2. Send a streaming Responses request carrying x-openai-internal-codex-responses-lite: true.
  3. Observe HTTP 200 and initial SSE events, followed by response.incomplete with reason adapter_eof; OpenCodex records 502.
  4. Replay the identical request after removing only the Lite header.
  5. Observe a normal response.completed terminal and successful Codex CLI exit.

The source behavior is also present on current dev: an adapter-boundary regression test expecting the Spark header to be absent fails before the proposed fix because the built request still contains true.

A failed WebSocket upgrade is not causal: Codex falls back to HTTP, and the HTTP request completes after the Lite header is removed.

Version

Observed on 2.43.0; source behavior confirmed on dev 2.47.0 at d00615d5696a9c6b7f1a3006181e57569b012920.

Operating system

Windows 10 Pro, build 19045

Provider and model

OpenAI (Codex login) / gpt-5.3-codex-spark

Logs or error output

With x-openai-internal-codex-responses-lite: true:
HTTP 200 -> SSE -> response.incomplete
incomplete_details.reason=adapter_eof
OpenCodex result: 502

Without that header:
HTTP 200 -> SSE -> response.completed
Codex output: SPARK_DROP_LITE_OK

Screenshots and supporting files

The result was reproduced by differential request replay. No credentials, account identifiers, request IDs, or private provider URLs are attached.

Redacted configuration

{
  "providers": {
    "openai": {
      "adapter": "openai-responses",
      "authMode": "forward",
      "baseUrl": "https://chatgpt.com/backend-api/codex"
    }
  }
}

Checks

  • I searched existing issues and documentation.
  • I removed secrets, tokens, account details, request credentials, and personal data.

Activity

  1. added
    bugSomething isn't working
    providerProvider adapters, OpenAI-compat presets, upstream API quirks
    streamingSSE, WebSocket, terminal stream frames
    on Sep 7, 2026
  2. lidge-jun commented on Sep 7, 2026

    @lidge-jun
    Owner

    리뷰 · 우선순위 71 / 80

    이 이슈는 Codex가 캐노니컬 ChatGPT Responses로 gpt-5.3-codex-spark를 쓸 때 x-openai-internal-codex-responses-lite: true가 붙으면 스트림이 터미널 없이 끝나고, OpenCodex가 adapter_eof / 502로 기록하는 버그입니다. 헤더만 제거한 동일 요청은 정상 response.completed로 끝납니다. WebSocket 업그레이드 실패가 원인이 아니라 HTTP 폴백 뒤에도 Lite 헤더가 남아 있는 것이 원인입니다.

    지금 dev(522ce5f8c)의 src/adapters/openai-responses.ts에도 Spark만 Lite를 끄는 예외는 아직 없습니다. 같은 작성자의 PR #3886이 최종 와이어 모델이 Spark일 때만 헤더를 지우고, Sol 등은 유지하며, 어댑터 경계 회귀 테스트까지 넣었습니다. 이슈 본문의 기대 동작과 PR 범위가 일치합니다.

    src/adapters/openai-responses.ts - 수정은 여기 한 지점이면 충분해 보입니다. 라우팅/인증/재시도는 건드리지 않는 편이 맞습니다.

    재현 절차 - 버전(2.43.0 관측, dev 2.47.0 소스 확인)과 redacted config가 충분합니다. 추가 로그 요청은 필요 없어 보입니다.

    메인테이너의 판단이 필요한 지점

    너의 추천
    #3886을 리뷰·머지하고 이 이슈는 그 PR로 닫으세요. 별도 설계 이슈로 열어 둘 이유는 없습니다.

    이 댓글은 grok-bot이 작성했습니다

  3. lidge-jun commented on Sep 7, 2026

    @lidge-jun
    Owner

    Fixed on dev by #3942, squash-merged as a13041740, carrying @cb8010d6's fix from #3886.

    The canonical adapter now removes x-openai-internal-codex-responses-lite — in every case spelling, covering both a caller-provided and a statically configured header — when the final serialized wire model is exactly gpt-5.3-codex-spark. It keys on the serialized body rather than parsed.modelId, so an alias that resolves to Spark is covered too, and other canonical models keep the header.

    One limit worth stating rather than leaving implicit: this covers the HTTP header replay path you reported, including the HTTP fallback. On the WebSocket path, codex-ws-request.ts writes the Lite metadata only when the header is present, so a client_metadata Lite value already in the body is not disabled by removing the header. Setting the header to "false" would cover that as well, but it exceeds this report and changes socket reuse identity, so it was deliberately left out. If you see adapter_eof on Spark over WebSocket after this lands in a release, please reopen or file a follow-up with that detail.

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

    bugSomething isn't workingproviderProvider adapters, OpenAI-compat presets, upstream API quirksstreamingSSE, WebSocket, terminal stream frames

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions