fix(cerebras): ensure all tools have consistent strict mode values (#10589)

Co-authored-by: Roo Code <roomote@roocode.com>
This commit is contained in:
roomote[bot] 2026-01-09 18:50:16 -07:00 committed by GitHub
parent 84789445cd
commit d97e540ac6
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 100 additions and 0 deletions

View file

@ -173,4 +173,77 @@ describe("CerebrasHandler", () => {
// Test fallback token estimation logic
})
})
describe("convertToolsForOpenAI", () => {
it("should set all tools to strict: false for Cerebras API consistency", () => {
// Access the protected method through a test subclass
const regularTool = {
type: "function",
function: {
name: "read_file",
parameters: {
type: "object",
properties: {
path: { type: "string" },
},
required: ["path"],
},
},
}
// MCP tool with the 'mcp--' prefix
const mcpTool = {
type: "function",
function: {
name: "mcp--server--tool",
parameters: {
type: "object",
properties: {
arg: { type: "string" },
},
},
},
}
// Create a test wrapper to access protected method
class TestCerebrasHandler extends CerebrasHandler {
public testConvertToolsForOpenAI(tools: any[]) {
return this.convertToolsForOpenAI(tools)
}
}
const testHandler = new TestCerebrasHandler({ cerebrasApiKey: "test" })
const converted = testHandler.testConvertToolsForOpenAI([regularTool, mcpTool])
// Both tools should have strict: false
expect(converted).toHaveLength(2)
expect(converted![0].function.strict).toBe(false)
expect(converted![1].function.strict).toBe(false)
})
it("should return undefined when tools is undefined", () => {
class TestCerebrasHandler extends CerebrasHandler {
public testConvertToolsForOpenAI(tools: any[] | undefined) {
return this.convertToolsForOpenAI(tools)
}
}
const testHandler = new TestCerebrasHandler({ cerebrasApiKey: "test" })
expect(testHandler.testConvertToolsForOpenAI(undefined)).toBeUndefined()
})
it("should pass through non-function tools unchanged", () => {
class TestCerebrasHandler extends CerebrasHandler {
public testConvertToolsForOpenAI(tools: any[]) {
return this.convertToolsForOpenAI(tools)
}
}
const nonFunctionTool = { type: "other", data: "test" }
const testHandler = new TestCerebrasHandler({ cerebrasApiKey: "test" })
const converted = testHandler.testConvertToolsForOpenAI([nonFunctionTool])
expect(converted![0]).toEqual(nonFunctionTool)
})
})
})

View file

@ -91,6 +91,33 @@ export class CerebrasHandler extends BaseProvider implements SingleCompletionHan
return result
}
/**
* Override convertToolsForOpenAI to ensure all tools have consistent strict values.
* Cerebras API requires all tools to have the same strict mode setting.
* We use strict: false for all tools since MCP tools cannot use strict mode
* (they have optional parameters from the MCP server schema).
*/
protected override convertToolsForOpenAI(tools: any[] | undefined): any[] | undefined {
if (!tools) {
return undefined
}
return tools.map((tool) => {
if (tool.type !== "function") {
return tool
}
return {
...tool,
function: {
...tool.function,
strict: false,
parameters: this.convertToolSchemaForOpenAI(tool.function.parameters),
},
}
})
}
async *createMessage(
systemPrompt: string,
messages: Anthropic.Messages.MessageParam[],