pull/5334/head
Aiden Cline 2025-12-10 11:11:04 -06:00
parent 83aa42f510
commit 996fb2a151
4 changed files with 45 additions and 22 deletions

View File

@ -74,6 +74,7 @@ export namespace ProviderTransform {
return result
}
// TODO: is this actually correct??? Or should it just match the other reasoning_content handling
// DeepSeek: Handle reasoning_content for tool call continuations
// - With tool calls: Include reasoning_content in providerOptions so model can continue reasoning
// - Without tool calls: Strip reasoning (new turn doesn't need previous reasoning)
@ -110,6 +111,45 @@ export namespace ProviderTransform {
content: filteredContent,
}
}
return msg
})
}
if (
model.capabilities.interleaved &&
typeof model.capabilities.interleaved === "object" &&
model.capabilities.interleaved.field === "reasoning_content"
) {
return msgs.map((msg) => {
if (msg.role === "assistant" && Array.isArray(msg.content)) {
const reasoningParts = msg.content.filter((part: any) => part.type === "reasoning")
const reasoningText = reasoningParts.map((part: any) => part.text).join("")
// Filter out reasoning parts from content
const filteredContent = msg.content.filter((part: any) => part.type !== "reasoning")
// Include reasoning_content directly on the message for all assistant messages
if (reasoningText) {
return {
...msg,
content: filteredContent,
providerOptions: {
...msg.providerOptions,
openaiCompatible: {
...(msg.providerOptions as any)?.openaiCompatible,
reasoning_content: reasoningText,
},
},
}
}
return {
...msg,
content: filteredContent,
}
}
return msg
})
}
@ -273,23 +313,7 @@ export namespace ProviderTransform {
return options
}
export function providerOptions(model: Provider.Model, options: { [x: string]: any }, messages: ModelMessage[]) {
if (model.capabilities.interleaved && typeof model.capabilities.interleaved === "object") {
const cot = []
const assistantMessages = messages.filter((msg) => msg.role === "assistant")
for (const msg of assistantMessages) {
for (const part of msg.content) {
if (typeof part === "string") {
continue
}
if (part.type === "reasoning") {
cot.push(part)
}
}
}
options[model.capabilities.interleaved.field] = cot
}
export function providerOptions(model: Provider.Model, options: { [x: string]: any }) {
switch (model.api.npm) {
case "@ai-sdk/openai":
case "@ai-sdk/azure":

View File

@ -143,7 +143,6 @@ export namespace SessionCompaction {
providerOptions: ProviderTransform.providerOptions(
model,
pipe({}, mergeDeep(ProviderTransform.options(model, input.sessionID)), mergeDeep(model.options)),
[],
),
headers: model.headers,
abortSignal: input.abort,

View File

@ -593,7 +593,7 @@ export namespace SessionPrompt {
OUTPUT_TOKEN_MAX,
),
abortSignal: abort,
providerOptions: ProviderTransform.providerOptions(model, params.options, messages),
providerOptions: ProviderTransform.providerOptions(model, params.options),
stopWhen: stepCountIs(1),
temperature: params.temperature,
topP: params.topP,
@ -1473,7 +1473,7 @@ export namespace SessionPrompt {
await generateText({
// use higher # for reasoning models since reasoning tokens eat up a lot of the budget
maxOutputTokens: small.capabilities.reasoning ? 3000 : 20,
providerOptions: ProviderTransform.providerOptions(small, options, []),
providerOptions: ProviderTransform.providerOptions(small, options),
messages: [
...SystemPrompt.title(small.providerID).map(
(x): ModelMessage => ({

View File

@ -91,7 +91,7 @@ export namespace SessionSummary {
if (textPart && !userMsg.summary?.title) {
const result = await generateText({
maxOutputTokens: small.capabilities.reasoning ? 1500 : 20,
providerOptions: ProviderTransform.providerOptions(small, options, []),
providerOptions: ProviderTransform.providerOptions(small, options),
messages: [
...SystemPrompt.title(small.providerID).map(
(x): ModelMessage => ({
@ -144,7 +144,7 @@ export namespace SessionSummary {
const result = await generateText({
model: language,
maxOutputTokens: 100,
providerOptions: ProviderTransform.providerOptions(small, options, []),
providerOptions: ProviderTransform.providerOptions(small, options),
messages: [
...SystemPrompt.summarize(small.providerID).map(
(x): ModelMessage => ({