Skip to content

fix(ai-vercel-gateway): surface delta.reasoning as reasoning events on chat completions - #2152

Open
pcbeingused333 wants to merge 2 commits into
TanStack:mainfrom
pcbeingused333:fix/c3284-vercel-gateway-reasoning
Open

pcbeingused333 wants to merge 2 commits into
TanStack:mainfrom
pcbeingused333:fix/c3284-vercel-gateway-reasoning

Conversation

@pcbeingused333

@pcbeingused333 pcbeingused333 commented Nov 14, 2026 •

Copy link
Copy Markdown
Contributor

The Vercel AI Gateway chat adapter sends chat({ reasoning }), and with the summary on the gateway streams the thinking text on delta.reasoning. The adapter never read that field. extractReasoning on the Chat Completions base returns undefined, so the thinking was dropped and no reasoning events were emitted.

🎯 Changes

packages/ai-vercel-gateway/src/adapters/text.ts overrides extractReasoning and returns { text } when delta.reasoning is a non-empty string. One unit regression test, a sentence on the adapter doc, and a patch changeset.

E2E: vercel-gateway joins the reasoning set in testing/e2e/src/lib/feature-support.ts. aimock emits delta.reasoning_content, so the provider factory in testing/e2e/src/lib/providers.ts passes a fetch that re-keys it to delta.reasoning, the same way openai-compatible-legacy re-keys its frames. The frame-rewriting stream is now one shared helper (sseRewriteFetch) used by both.

✅ Checklist

  • I have followed the steps in the Contributing guide.
  • I have tested code changes locally with pnpm run test:pr, or these tests do not apply to this pull request. (The @tanstack/ai-vercel-gateway vitest suite, the reasoning and chat E2E specs, tsc --noEmit, oxlint src --type-aware and oxfmt --check were run. The full test:pr was not.)
  • I fully understand the code in this pull request, including any code generated with AI assistance.
  • Docs: I updated docs/ for this change, or this change is not user-facing.
  • Changeset: I added a changeset (pnpm changeset), or this PR does not change a published package.

🚀 Release Impact

  • This change affects published code, and I have generated a changeset.
  • This change is docs/CI/dev-only (no release).

Root cause

Issue. A Chat Completions stream with reasoning summary on produces no reasoning events. The answer text still arrives.
Cause. Vercel documents that reasoning content is streamed incrementally in delta.reasoning. That field is outside the OpenAI Chat Completions chunk type, and the base extractReasoning returns undefined. The request side already sends the gateway reasoning object, and adds exclude: true only when the summary is off.
Fix. Override extractReasoning and read delta.reasoning. An empty string or a non-string is ignored. The Responses adapter is unchanged.

Possible alternatives

Also accept delta.reasoning_content, as the LLM Gateway and Cloudflare adapters do. Vercel's Chat Completions docs name delta.reasoning only, so this change reads that field and nothing else.

Testing

In Docker node:22, after pnpm install --frozen-lockfile --filter @tanstack/ai-vercel-gateway... and building the package's workspace dependencies.

With packages/ai-vercel-gateway/src/adapters/text.ts from main and the new test:

Test Files  1 failed (1)
Tests  1 failed | 4 passed (5)  [tests/text-adapter.test.ts]

With this change, npx vitest run --no-cache in packages/ai-vercel-gateway:

Test Files  16 passed (16)
Tests  65 passed (65)

tsc --noEmit and oxfmt --check on the adapter, the test, the doc sentence and the changeset pass. oxlint src --type-aware reports no new errors.

E2E, same image, after pnpm install --frozen-lockfile --filter @tanstack/ai-e2e..., building the workspace dependencies and npx playwright install --with-deps chromium, full provider matrix (CI=1).

With the adapter source from main rebuilt, npx playwright test tests/reasoning.spec.ts:

1 failed
  [chromium] › tests/reasoning.spec.ts:12:5 › vercel-gateway — reasoning › shows thinking block and final answer
11 passed

With this change rebuilt, npx playwright test tests/reasoning.spec.ts tests/chat.spec.ts:

69 passed

tsc --noEmit in testing/e2e and oxfmt --check on the two E2E files pass. The full pnpm test:pr and the rest of the E2E suite were not run. No call to the live gateway was made; the unit test mocks the SDK and the E2E run uses aimock.

Manual check:

  1. Restore packages/ai-vercel-gateway/src/adapters/text.ts from main, then run npx vitest run tests/text-adapter.test.ts in packages/ai-vercel-gateway. The delta.reasoning test fails.
  2. Restore this branch's file and run npx vitest run in that package. The suite passes.
  3. In testing/e2e, run CI=1 npx playwright test tests/reasoning.spec.ts (full matrix; E2E_PROVIDERS=vercel-gateway without CI narrows it to this provider). The vercel-gateway case shows the thinking block.

Risk / rollback

Low risk: chunks without a non-empty string delta.reasoning behave as before. Revert this PR to drop the thinking text again.

AI assistance was used to prepare this change and its tests.

Summary by CodeRabbit

  • Bug Fixes
    • Chat Completions streams now surface gateway reasoning text as reasoning events, including when a reasoning summary is enabled. Reasoning chunks are emitted in order before text begins.
  • Tests
    • Added coverage for gateway reasoning streams and for streams that contain no reasoning content.
  • Documentation
    • Clarified how reasoning text is handled in Vercel Gateway Chat Completions streams.

…n chat completions

AI Gateway streams thinking text on delta.reasoning when chat({ reasoning })
leaves the summary on. The chat adapter never overrode extractReasoning, so
the base dropped that text and no reasoning events were emitted.
Re-key aimock's delta.reasoning_content to delta.reasoning for the
vercel-gateway chat provider and add it to the reasoning matrix, so the
adapter's extractReasoning override runs end-to-end.
@changeset-bot

changeset-bot Bot commented Nov 14, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 0e92bf9

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 1 package
Name Type
@tanstack/ai-vercel-gateway Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@coderabbitai

coderabbitai Bot commented Nov 14, 2026 •

Copy link
Copy Markdown
Contributor

Explain Change →

No actionable comments were generated in the recent review.

Walkthrough

The Vercel Gateway text adapter now emits reasoning events from nonempty Chat Completions delta.reasoning values. End-to-end test support maps fixture reasoning fields and includes Vercel Gateway in the reasoning feature matrix.

Changes: Vercel Gateway reasoning

Layer / File(s) Summary
Extract and test reasoning deltas
packages/ai-vercel-gateway/src/adapters/text.ts, packages/ai-vercel-gateway/tests/text-adapter.test.ts, docs/adapters/vercel-gateway.md, .changeset/vercel-gateway-stream-reasoning.md
The adapter extracts nonempty reasoning strings from the first choice’s delta. Tests check reasoning event order, text output, and the absence of reasoning events for a text-only chunk. The documentation and changeset describe the behavior.
Map reasoning fields in end-to-end tests
testing/e2e/src/lib/providers.ts, testing/e2e/src/lib/feature-support.ts
SSE rewrite helpers map legacy Bedrock and Vercel Gateway reasoning fields. The Vercel Gateway chat adapter uses its rewrite, and the reasoning feature matrix includes the provider.

Estimated code review effort: 2 (Simple) | ~12 minutes

Change: Bug fix

Suggested reviewers: alemtuzlak, jsve, tombeckenham

Merge Risk: Minimal · up to 0e92b

This change surfaces Vercel Gateway reasoning text from Chat Completions streams as reasoning events. No merge-blocking risk was identified.

Pre-merge checks: Passed 4

Check name Status Explanation
Title check Passed The title names the package and the main fix: the Vercel AI Gateway Chat Completions path now surfaces delta.reasoning as reasoning events. This matches the adapter override, the unit test, and the ch…
Description check Passed The description follows the template. It has the Changes section, with the adapter override, test, doc sentence, changeset, and E2E changes. The checklist is filled in, with the test:pr item left unch…
Linked Issues check Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check Passed Check skipped because no linked issues were found for this pull request.
Full details: Title check

Explanation

The title names the package and the main fix: the Vercel AI Gateway Chat Completions path now surfaces delta.reasoning as reasoning events. This matches the adapter override, the unit test, and the changeset. The title is long (87 characters) but it is specific and accurate.

Full details: Description check

Explanation

The description follows the template. It has the Changes section, with the adapter override, test, doc sentence, changeset, and E2E changes. The checklist is filled in, with the test:pr item left unchecked and explained. Release Impact is marked. It also adds Root cause, Alternatives, Testing, and Risk sections with concrete commands and results. The template's required items are all present.

Finishing Touches

Generate unit tests (beta)

  • Create a new PR
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

Share

Recent review info

Run configuration

  • Source mode: Auto
  • Repository: TanStack/ai
  • Branch: main
  • File: .coderabbit.yaml
  • Commit: 1888233
  • Layers: Repository YAML
  • Review profile: CHILL
  • Plan: Advanced
  • Run ID: b24eb719-6b85-411a-82ca-678f30806133
Commits

Reviewing files that changed from the base of the PR and between 1888233 and 0e92bf9.

Files selected for processing: 6

  • .changeset/vercel-gateway-stream-reasoning.md
  • docs/adapters/vercel-gateway.md
  • packages/ai-vercel-gateway/src/adapters/text.ts
  • packages/ai-vercel-gateway/tests/text-adapter.test.ts
  • testing/e2e/src/lib/feature-support.ts
  • testing/e2e/src/lib/providers.ts

Included review availability: This review used your included allowance. Your plan provides up to 8 included reviews per hour; 7 remain after this review.

@github-actions

Copy link
Copy Markdown
Contributor

Thanks for the PR, @pcbeingused333! 🙌 @jherr will take a look.

Automated pre-review checks

  • ✅ CI passing
  • ✅ No merge conflicts
  • ✅ Changeset present
  • ✅ E2E test changes included

Automated triage — a human review follows.

@github-actions github-actions Bot added the waiting-on: maintainer The ball is in the maintainers’ court label Nov 14, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

waiting-on: maintainer The ball is in the maintainers’ court

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants