feat: allow custom model ID passthrough for Vertex AI providers

- Add gemini-3.1-flash-lite-preview to vertex models list
- Update VertexHandler.getModel() to pass through unknown model IDs
  with sensible default ModelInfo instead of falling back to default model
- Update AnthropicVertexHandler.getModel() with same custom model ID
  passthrough behavior
- Add tests for custom model ID passthrough in both handlers

Closes #12232
This commit is contained in:
Roo Code 2026-05-08 05:28:36 +00:00
parent ad25634905
commit edbd11269a
5 changed files with 111 additions and 4 deletions

View file

@ -35,6 +35,17 @@ export const vertexModels = {
},
],
},
"gemini-3.1-flash-lite-preview": {
maxTokens: 65_536,
contextWindow: 1_048_576,
supportsImages: true,
supportsPromptCache: true,
supportsTemperature: true,
defaultTemperature: 1,
inputPrice: 0.0,
outputPrice: 0.0,
},
"gemini-3.1-pro-preview-customtools": {
maxTokens: 65_536,
contextWindow: 1_048_576,

View file

@ -869,6 +869,34 @@ describe("VertexHandler", () => {
expect(result.temperature).toBe(0)
})
it("should pass through custom/unknown model IDs with sensible defaults", () => {
const handler = new AnthropicVertexHandler({
apiModelId: "claude-5-opus@20260101",
vertexProjectId: "test-project",
vertexRegion: "us-central1",
})
const modelInfo = handler.getModel()
expect(modelInfo.id).toBe("claude-5-opus@20260101")
expect(modelInfo.info).toBeDefined()
expect(modelInfo.info.maxTokens).toBe(8192)
expect(modelInfo.info.contextWindow).toBe(200_000)
expect(modelInfo.info.supportsImages).toBe(true)
expect(modelInfo.info.supportsPromptCache).toBe(false)
})
it("should fall back to default model when no model ID is provided", () => {
const handler = new AnthropicVertexHandler({
vertexProjectId: "test-project",
vertexRegion: "us-central1",
})
const modelInfo = handler.getModel()
expect(modelInfo.id).toBeDefined()
expect(modelInfo.info).toBeDefined()
expect(modelInfo.info.maxTokens).toBeGreaterThan(0)
})
it("should enable 1M context for Claude Sonnet 4 when beta flag is set", () => {
const handler = new AnthropicVertexHandler({
apiModelId: VERTEX_1M_CONTEXT_MODEL_IDS[0],

View file

@ -163,5 +163,35 @@ describe("VertexHandler", () => {
expect(excludedCount).toBe(1)
expect(includedCount).toBe(1)
})
it("should pass through custom/unknown model IDs with sensible defaults", () => {
const testHandler = new VertexHandler({
apiModelId: "gemini-4.0-ultra-preview",
vertexProjectId: "test-project",
vertexRegion: "us-central1",
})
const modelInfo = testHandler.getModel()
expect(modelInfo.id).toBe("gemini-4.0-ultra-preview")
expect(modelInfo.info).toBeDefined()
expect(modelInfo.info.maxTokens).toBe(8192)
expect(modelInfo.info.contextWindow).toBe(1_048_576)
expect(modelInfo.info.supportsImages).toBe(true)
expect(modelInfo.info.supportsPromptCache).toBe(false)
expect(modelInfo.info.excludedTools).toContain("apply_diff")
expect(modelInfo.info.includedTools).toContain("edit")
})
it("should fall back to default model when no model ID is provided", () => {
const testHandler = new VertexHandler({
vertexProjectId: "test-project",
vertexRegion: "us-central1",
})
const modelInfo = testHandler.getModel()
expect(modelInfo.id).toBeDefined()
expect(modelInfo.info).toBeDefined()
expect(modelInfo.info.maxTokens).toBeGreaterThan(0)
})
})
})

View file

@ -207,8 +207,27 @@ export class AnthropicVertexHandler extends BaseProvider implements SingleComple
getModel() {
const modelId = this.options.apiModelId
let id = modelId && modelId in vertexModels ? (modelId as VertexModelId) : vertexDefaultModelId
let info: ModelInfo = vertexModels[id]
let id: string
let info: ModelInfo
if (modelId && modelId in vertexModels) {
id = modelId as VertexModelId
info = vertexModels[id as VertexModelId]
} else if (modelId) {
// Pass through custom/unknown model IDs with sensible defaults
id = modelId
info = {
maxTokens: 8192,
contextWindow: 200_000,
supportsImages: true,
supportsPromptCache: false,
inputPrice: 0,
outputPrice: 0,
}
} else {
id = vertexDefaultModelId
info = vertexModels[vertexDefaultModelId]
}
// Check if 1M context beta should be enabled for supported models
const supports1MContext = VERTEX_1M_CONTEXT_MODEL_IDS.includes(

View file

@ -14,8 +14,27 @@ export class VertexHandler extends GeminiHandler implements SingleCompletionHand
override getModel() {
const modelId = this.options.apiModelId
let id = modelId && modelId in vertexModels ? (modelId as VertexModelId) : vertexDefaultModelId
let info: ModelInfo = vertexModels[id]
let id: string
let info: ModelInfo
if (modelId && modelId in vertexModels) {
id = modelId as VertexModelId
info = vertexModels[id as VertexModelId]
} else if (modelId) {
// Pass through custom/unknown model IDs with sensible defaults
id = modelId
info = {
maxTokens: 8192,
contextWindow: 1_048_576,
supportsImages: true,
supportsPromptCache: false,
inputPrice: 0,
outputPrice: 0,
}
} else {
id = vertexDefaultModelId
info = vertexModels[vertexDefaultModelId]
}
const params = getModelParams({
format: "gemini",
modelId: id,