Skip to content

Commit b4d9f92

Browse files
Revert "Fix provider 400s: strip reasoning_details from messages, $ref from tool schemas" (#11453)
1 parent 3965cd9 commit b4d9f92

24 files changed

Lines changed: 60 additions & 419 deletions

src/api/providers/__tests__/anthropic-vertex.spec.ts

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -246,21 +246,20 @@ describe("AnthropicVertexHandler", () => {
246246
)
247247
})
248248

249-
it("should sanitize and pass messages to streamText as ModelMessage[]", async () => {
249+
it("should pass messages directly to streamText as ModelMessage[]", async () => {
250250
mockStreamText.mockReturnValue(createMockStreamResult([]))
251251

252252
const stream = handler.createMessage(systemPrompt, mockMessages)
253253
for await (const _chunk of stream) {
254254
// consume
255255
}
256256

257-
// Messages are sanitized (allowlist: role, content, providerOptions) before passing to streamText
258-
const callArgs = mockStreamText.mock.calls[0]![0]
259-
expect(callArgs.messages).toHaveLength(2)
260-
expect(callArgs.messages[0].role).toBe("user")
261-
expect(callArgs.messages[0].content).toBe("Hello")
262-
expect(callArgs.messages[1].role).toBe("assistant")
263-
expect(callArgs.messages[1].content).toBe("Hi there!")
257+
// Messages are now already in ModelMessage format, passed directly to streamText
258+
expect(mockStreamText).toHaveBeenCalledWith(
259+
expect.objectContaining({
260+
messages: mockMessages,
261+
}),
262+
)
264263
})
265264

266265
it("should pass tools through AI SDK conversion pipeline", async () => {

src/api/providers/__tests__/anthropic.spec.ts

Lines changed: 0 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -399,45 +399,6 @@ describe("AnthropicHandler", () => {
399399
expect(endChunk).toBeDefined()
400400
})
401401

402-
it("should strip reasoning_details and reasoning_content from messages before sending to API", async () => {
403-
setupStreamTextMock([{ type: "text-delta", text: "test" }])
404-
405-
// Simulate messages with extra legacy fields that survive JSON deserialization
406-
const messagesWithExtraFields = [
407-
{
408-
role: "user",
409-
content: [{ type: "text" as const, text: "Hello" }],
410-
},
411-
{
412-
role: "assistant",
413-
content: [{ type: "text" as const, text: "Hi" }],
414-
reasoning_details: [{ type: "thinking", thinking: "some reasoning" }],
415-
reasoning_content: "some reasoning content",
416-
},
417-
{
418-
role: "user",
419-
content: [{ type: "text" as const, text: "Follow up" }],
420-
},
421-
] as any
422-
423-
const stream = handler.createMessage(systemPrompt, messagesWithExtraFields)
424-
425-
for await (const _chunk of stream) {
426-
// Consume stream
427-
}
428-
429-
// Verify streamText was called exactly once
430-
expect(mockStreamText).toHaveBeenCalledTimes(1)
431-
const callArgs = mockStreamText.mock.calls[0]![0]
432-
for (const msg of callArgs.messages) {
433-
expect(msg).not.toHaveProperty("reasoning_details")
434-
expect(msg).not.toHaveProperty("reasoning_content")
435-
}
436-
// Verify the rest of the message is preserved
437-
expect(callArgs.messages[1].role).toBe("assistant")
438-
expect(callArgs.messages[1].content).toEqual([{ type: "text", text: "Hi" }])
439-
})
440-
441402
it("should pass system prompt via system param when no systemProviderOptions", async () => {
442403
setupStreamTextMock([{ type: "text-delta", text: "test" }])
443404

src/api/providers/anthropic-vertex.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import type { Anthropic } from "@anthropic-ai/sdk"
22
import { createVertexAnthropic } from "@ai-sdk/google-vertex/anthropic"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import {
66
type ModelInfo,
@@ -28,7 +28,6 @@ import {
2828
} from "../transform/ai-sdk"
2929
import { applyToolCacheOptions, applySystemPromptCaching } from "../transform/cache-breakpoints"
3030
import { calculateApiCostAnthropic } from "../../shared/cost"
31-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
3231

3332
import { DEFAULT_HEADERS } from "./constants"
3433
import { BaseProvider } from "./base-provider"
@@ -92,8 +91,8 @@ export class AnthropicVertexHandler extends BaseProvider implements SingleComple
9291
): ApiStream {
9392
const modelConfig = this.getModel()
9493

95-
// Sanitize messages for the provider API (allowlist: role, content, providerOptions).
96-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
94+
// Convert messages to AI SDK format
95+
const aiSdkMessages = messages as ModelMessage[]
9796

9897
// Convert tools to AI SDK format
9998
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)

src/api/providers/anthropic.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import { createAnthropic } from "@ai-sdk/anthropic"
2-
import { streamText, generateText, ToolSet } from "ai"
2+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
33

44
import {
55
type ModelInfo,
@@ -26,7 +26,6 @@ import {
2626
} from "../transform/ai-sdk"
2727
import { applyToolCacheOptions, applySystemPromptCaching } from "../transform/cache-breakpoints"
2828
import { calculateApiCostAnthropic } from "../../shared/cost"
29-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
3029

3130
import { DEFAULT_HEADERS } from "./constants"
3231
import { BaseProvider } from "./base-provider"
@@ -78,8 +77,8 @@ export class AnthropicHandler extends BaseProvider implements SingleCompletionHa
7877
): ApiStream {
7978
const modelConfig = this.getModel()
8079

81-
// Sanitize messages for the provider API (allowlist: role, content, providerOptions).
82-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
80+
// Convert messages to AI SDK format
81+
const aiSdkMessages = messages as ModelMessage[]
8382

8483
// Convert tools to AI SDK format
8584
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)

src/api/providers/azure.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { Anthropic } from "@anthropic-ai/sdk"
22
import { createAzure } from "@ai-sdk/azure"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import { azureModels, azureDefaultModelInfo, type ModelInfo } from "@roo-code/types"
66

@@ -21,7 +21,6 @@ import { DEFAULT_HEADERS } from "./constants"
2121
import { BaseProvider } from "./base-provider"
2222
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2323
import type { RooMessage } from "../../core/task-persistence/rooMessage"
24-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2524

2625
const AZURE_DEFAULT_TEMPERATURE = 0
2726

@@ -155,8 +154,8 @@ export class AzureHandler extends BaseProvider implements SingleCompletionHandle
155154
const { temperature } = this.getModel()
156155
const languageModel = this.getLanguageModel()
157156

158-
// Sanitize messages for the provider API (allowlist: role, content, providerOptions).
159-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
157+
// Convert messages to AI SDK format
158+
const aiSdkMessages = messages as ModelMessage[]
160159

161160
// Convert tools to OpenAI format first, then to AI SDK format
162161
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)

src/api/providers/baseten.ts

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { Anthropic } from "@anthropic-ai/sdk"
22
import { createBaseten } from "@ai-sdk/baseten"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import { basetenModels, basetenDefaultModelId, type ModelInfo } from "@roo-code/types"
66

@@ -21,7 +21,6 @@ import { DEFAULT_HEADERS } from "./constants"
2121
import { BaseProvider } from "./base-provider"
2222
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2323
import type { RooMessage } from "../../core/task-persistence/rooMessage"
24-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2524

2625
const BASETEN_DEFAULT_TEMPERATURE = 0.5
2726

@@ -116,7 +115,7 @@ export class BasetenHandler extends BaseProvider implements SingleCompletionHand
116115
const { temperature } = this.getModel()
117116
const languageModel = this.getLanguageModel()
118117

119-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
118+
const aiSdkMessages = messages as ModelMessage[]
120119

121120
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)
122121
const aiSdkTools = convertToolsForAiSdk(openAiTools) as ToolSet | undefined

src/api/providers/deepseek.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { Anthropic } from "@anthropic-ai/sdk"
22
import { createDeepSeek } from "@ai-sdk/deepseek"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import { deepSeekModels, deepSeekDefaultModelId, DEEP_SEEK_DEFAULT_TEMPERATURE, type ModelInfo } from "@roo-code/types"
66

@@ -21,7 +21,6 @@ import { DEFAULT_HEADERS } from "./constants"
2121
import { BaseProvider } from "./base-provider"
2222
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2323
import type { RooMessage } from "../../core/task-persistence/rooMessage"
24-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2524

2625
/**
2726
* DeepSeek provider using the dedicated @ai-sdk/deepseek package.
@@ -134,8 +133,8 @@ export class DeepSeekHandler extends BaseProvider implements SingleCompletionHan
134133
const { temperature } = this.getModel()
135134
const languageModel = this.getLanguageModel()
136135

137-
// Sanitize messages for the provider API (allowlist: role, content, providerOptions).
138-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
136+
// Convert messages to AI SDK format
137+
const aiSdkMessages = messages as ModelMessage[]
139138

140139
// Convert tools to OpenAI format first, then to AI SDK format
141140
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)

src/api/providers/fireworks.ts

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { Anthropic } from "@anthropic-ai/sdk"
22
import { createFireworks } from "@ai-sdk/fireworks"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import { fireworksModels, fireworksDefaultModelId, type ModelInfo } from "@roo-code/types"
66

@@ -21,7 +21,6 @@ import { DEFAULT_HEADERS } from "./constants"
2121
import { BaseProvider } from "./base-provider"
2222
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2323
import type { RooMessage } from "../../core/task-persistence/rooMessage"
24-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2524

2625
const FIREWORKS_DEFAULT_TEMPERATURE = 0.5
2726

@@ -134,8 +133,8 @@ export class FireworksHandler extends BaseProvider implements SingleCompletionHa
134133
const { temperature } = this.getModel()
135134
const languageModel = this.getLanguageModel()
136135

137-
// Sanitize messages for the provider API (allowlist: role, content, providerOptions).
138-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
136+
// Convert messages to AI SDK format
137+
const aiSdkMessages = messages as ModelMessage[]
139138

140139
// Convert tools to OpenAI format first, then to AI SDK format
141140
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)

src/api/providers/lm-studio.ts

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,13 @@
11
import { Anthropic } from "@anthropic-ai/sdk"
2-
import { streamText, generateText, ToolSet, wrapLanguageModel, extractReasoningMiddleware, LanguageModel } from "ai"
2+
import {
3+
streamText,
4+
generateText,
5+
ToolSet,
6+
wrapLanguageModel,
7+
extractReasoningMiddleware,
8+
LanguageModel,
9+
ModelMessage,
10+
} from "ai"
311

412
import { type ModelInfo, openAiModelInfoSaneDefaults, LMSTUDIO_DEFAULT_TEMPERATURE } from "@roo-code/types"
513

@@ -19,7 +27,6 @@ import { OpenAICompatibleHandler, OpenAICompatibleConfig } from "./openai-compat
1927
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2028
import { getModelsFromCache } from "./fetchers/modelCache"
2129
import type { RooMessage } from "../../core/task-persistence/rooMessage"
22-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2330

2431
export class LmStudioHandler extends OpenAICompatibleHandler implements SingleCompletionHandler {
2532
constructor(options: ApiHandlerOptions) {
@@ -58,7 +65,7 @@ export class LmStudioHandler extends OpenAICompatibleHandler implements SingleCo
5865
const model = this.getModel()
5966
const languageModel = this.getLanguageModel()
6067

61-
const aiSdkMessages = sanitizeMessagesForProvider(messages)
68+
const aiSdkMessages = messages as ModelMessage[]
6269

6370
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)
6471
const aiSdkTools = convertToolsForAiSdk(openAiTools) as ToolSet | undefined

src/api/providers/minimax.ts

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import type { Anthropic } from "@anthropic-ai/sdk"
22
import { createAnthropic } from "@ai-sdk/anthropic"
3-
import { streamText, generateText, ToolSet } from "ai"
3+
import { streamText, generateText, ToolSet, ModelMessage } from "ai"
44

55
import { type ModelInfo, minimaxDefaultModelId, minimaxModels } from "@roo-code/types"
66

@@ -23,7 +23,6 @@ import { DEFAULT_HEADERS } from "./constants"
2323
import { BaseProvider } from "./base-provider"
2424
import type { SingleCompletionHandler, ApiHandlerCreateMessageMetadata } from "../index"
2525
import type { RooMessage } from "../../core/task-persistence/rooMessage"
26-
import { sanitizeMessagesForProvider } from "../transform/sanitize-messages"
2726

2827
export class MiniMaxHandler extends BaseProvider implements SingleCompletionHandler {
2928
private client: ReturnType<typeof createAnthropic>
@@ -74,7 +73,7 @@ export class MiniMaxHandler extends BaseProvider implements SingleCompletionHand
7473
})
7574

7675
const mergedMessages = mergeEnvironmentDetailsForMiniMax(messages as any)
77-
const aiSdkMessages = sanitizeMessagesForProvider(mergedMessages as RooMessage[])
76+
const aiSdkMessages = mergedMessages as ModelMessage[]
7877
const openAiTools = this.convertToolsForOpenAI(metadata?.tools)
7978
const aiSdkTools = convertToolsForAiSdk(openAiTools) as ToolSet | undefined
8079
applyToolCacheOptions(aiSdkTools as Parameters<typeof applyToolCacheOptions>[0], metadata?.toolProviderOptions)

0 commit comments

Comments
 (0)