Skip to content

fix: preserve response headers on parsing and stream errors - #922

Open
sylvesterkaczmarek wants to merge 8 commits into
openai:mainfrom
sylvesterkaczmarek:fix/exception-response-headers
Open

fix: preserve response headers on parsing and stream errors#922
sylvesterkaczmarek wants to merge 8 commits into
openai:mainfrom
sylvesterkaczmarek:fix/exception-response-headers

Conversation

@sylvesterkaczmarek

@sylvesterkaczmarek sylvesterkaczmarek commented Aug 21, 2026

Copy link
Copy Markdown

This pull request preserves available HTTP response headers when response parsing or streaming fails, so callers can inspect diagnostics such as x-request-id.

Problem

OpenAIInvalidDataException and OpenAIIoException currently carry only a message and cause. This drops response metadata even in error paths where an HttpResponse already exists:

  • JsonHandler wraps body read/deserialization failures as OpenAIInvalidDataException.
  • StreamHandler wraps reader IOExceptions as OpenAIIoException.

That makes production debugging harder because callers cannot recover response headers such as x-request-id.

Changes

  • add optional headers() accessors to OpenAIInvalidDataException and OpenAIIoException
  • keep the existing two-parameter primary constructors unchanged
  • use internal secondary constructors only when response headers are available
  • attach response.headers() when JSON body parsing fails
  • attach response headers when a streaming reader fails
  • leave pre-response transport failures unchanged, where no response headers exist
  • add focused regression coverage for both error paths

Compatibility

The original primary constructor signatures and Kotlin default-argument ABI remain unchanged, and the existing Java overloads are preserved. The new header metadata is additive and optional.

Validation

  • verified the branch is based on upstream main at 95f4a1173c119ad08a049d752ec67de251434938
  • verified the diff is limited to the two exception types, the JSON/stream handlers, and focused tests
  • focused regression tests are included for x-request-id propagation
  • full repository validation is left to GitHub Actions because this environment does not have a complete local checkout/toolchain

Fixes #690

@sylvesterkaczmarek
sylvesterkaczmarek requested a review from a team as a code owner August 21, 2026 00:52

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: df0e205eff

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

constructor(
message: String? = null,
cause: Throwable? = null,
private val headers: Headers? = null,

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Preserve the original Kotlin constructor ABI

Adding headers to the primary constructor changes its synthetic default-argument descriptor; @JvmOverloads preserves the Java overloads but not that Kotlin ABI. A Kotlin consumer compiled against the previous release using OpenAIInvalidDataException("message") invokes the old (String, Throwable, int, DefaultConstructorMarker) constructor and will get NoSuchMethodError after upgrading without recompilation. Keep the original two-parameter primary constructor and introduce header support without replacing its default constructor; the identical change in OpenAIIoException.kt needs the same treatment.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in the latest commits. Both exception classes now keep the original two-parameter primary constructor unchanged and use an internal three-argument secondary constructor only when response headers are available. This preserves the existing Kotlin default-argument constructor ABI while keeping the new optional headers() accessor.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Make request/response info available in OpenAIException when available

1 participant