From ea19cc9dc459bd259e27f7fcc29601a010c5f8f0 Mon Sep 17 00:00:00 2001 From: hugocasa Date: Mon, 6 Jul 2026 11:26:24 +0200 Subject: [PATCH] fix(ai): test key routes Azure Foundry Claude models via Anthropic Messages API (#9956) Co-authored-by: Claude Opus 4.8 (1M context) --- frontend/src/lib/components/copilot/lib.ts | 21 +++++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/frontend/src/lib/components/copilot/lib.ts b/frontend/src/lib/components/copilot/lib.ts index 52896f0d80..323b552cca 100644 --- a/frontend/src/lib/components/copilot/lib.ts +++ b/frontend/src/lib/components/copilot/lib.ts @@ -14,7 +14,7 @@ import Anthropic from '@anthropic-ai/sdk' import { get, type Writable } from 'svelte/store' import { OpenAPI, ResourceService, type Script } from '../../gen' import { EDIT_CONFIG, FIX_CONFIG, GEN_CONFIG } from './prompts' -import { requiresMaxCompletionTokens } from './modelConfig' +import { requiresMaxCompletionTokens, usesAnthropicMessagesApi } from './modelConfig' import { applyReasoningToConfig } from './reasoningRegistry' import { formatResourceTypes } from './utils' import { processToolCall, type Tool, type ToolCallbacks } from './chat/shared' @@ -466,15 +466,19 @@ export async function testKey({ throw new Error('Missing a model to test') } - // Use Anthropic SDK for Anthropic provider - if (aiProvider === 'anthropic') { + // Providers served through the Anthropic Messages API (native Anthropic, and + // Claude deployments on Azure Foundry) must use the Anthropic SDK path rather + // than OpenAI chat completions. Mirrors the chat loop's routing so the test + // key exercises the same request shape the chat actually sends. + if (usesAnthropicMessagesApi(aiProvider, modelToTest)) { await testAnthropicKey({ apiKey, workspace, resourcePath, model: modelToTest, abortController, - messages + messages, + aiProvider }) return } @@ -496,7 +500,8 @@ async function testAnthropicKey({ resourcePath, model, abortController, - messages + messages, + aiProvider }: { apiKey?: string workspace?: string @@ -504,11 +509,15 @@ async function testAnthropicKey({ model: string abortController: AbortController messages: ChatCompletionMessageParam[] + aiProvider: AIProvider }) { const { system, messages: anthropicMessages } = convertOpenAIToAnthropicMessages(messages) + // X-Provider must be the real provider (e.g. azure_foundry) so the backend + // resolves the right credentials and Anthropic URL; the SDK headers tell it to + // route through the Anthropic Messages API. const headers: Record = { - 'X-Provider': 'anthropic', + 'X-Provider': aiProvider, 'anthropic-version': '2023-06-01', 'X-Anthropic-SDK': 'true' }