Download src/utils/model/validateModel.ts from chenbhao/codev: direct link, hf CLI and curl.
- Browser
- Download file 4.63 kB
-
https://huggingface.co/chenbhao/codev/resolve/main/src/utils/model/validateModel.ts
- Command line
-
hf download hf://chenbhao/codev/src/utils/model/validateModel.ts
-
curl -L -o validateModel.ts https://huggingface.co/chenbhao/codev/resolve/main/src/utils/model/validateModel.ts
4.63 kB
| // biome-ignore-all assist/source/organizeImports: ANT-ONLY import markers must not be reordered | |
| import { MODEL_ALIASES } from './aliases.js' | |
| import { isModelAllowed } from './modelAllowlist.js' | |
| import { getAPIProvider } from './providers.js' | |
| import { sideQuery } from '../sideQuery.js' | |
| import { | |
| NotFoundError, | |
| APIError, | |
| APIConnectionError, | |
| AuthenticationError, | |
| } from '@anthropic-ai/sdk' | |
| import { getModelStrings } from './modelStrings.js' | |
| // Cache valid models to avoid repeated API calls | |
| const validModelCache = new Map<string, boolean>() | |
| /** | |
| * Validates a model by attempting an actual API call. | |
| */ | |
| export async function validateModel( | |
| model: string, | |
| ): Promise<{ valid: boolean; error?: string }> { | |
| const normalizedModel = model.trim() | |
| // Empty model is invalid | |
| if (!normalizedModel) { | |
| return { valid: false, error: 'Model name cannot be empty' } | |
| } | |
| // Check against availableModels allowlist before any API call | |
| if (!isModelAllowed(normalizedModel)) { | |
| return { | |
| valid: false, | |
| error: `Model '${normalizedModel}' is not in the list of available models`, | |
| } | |
| } | |
| // Check if it's a known alias (these are always valid) | |
| const lowerModel = normalizedModel.toLowerCase() | |
| if ((MODEL_ALIASES as readonly string[]).includes(lowerModel)) { | |
| return { valid: true } | |
| } | |
| // Check if it matches ANTHROPIC_CUSTOM_MODEL_OPTION (pre-validated by the user) | |
| if (normalizedModel === process.env.ANTHROPIC_CUSTOM_MODEL_OPTION) { | |
| return { valid: true } | |
| } | |
| // Check cache first | |
| if (validModelCache.has(normalizedModel)) { | |
| return { valid: true } | |
| } | |
| // Try to make an actual API call with minimal parameters | |
| try { | |
| await sideQuery({ | |
| model: normalizedModel, | |
| max_tokens: 1, | |
| maxRetries: 0, | |
| querySource: 'model_validation', | |
| messages: [ | |
| { | |
| role: 'user', | |
| content: [ | |
| { | |
| type: 'text', | |
| text: 'Hi', | |
| cache_control: { type: 'ephemeral' }, | |
| }, | |
| ], | |
| }, | |
| ], | |
| }) | |
| // If we got here, the model is valid | |
| validModelCache.set(normalizedModel, true) | |
| return { valid: true } | |
| } catch (error) { | |
| return handleValidationError(error, normalizedModel) | |
| } | |
| } | |
| function handleValidationError( | |
| error: unknown, | |
| modelName: string, | |
| ): { valid: boolean; error: string } { | |
| // NotFoundError (404) means the model doesn't exist | |
| if (error instanceof NotFoundError) { | |
| const fallback = get3PFallbackSuggestion(modelName) | |
| const suggestion = fallback ? `. Try '${fallback}' instead` : '' | |
| return { | |
| valid: false, | |
| error: `Model '${modelName}' not found${suggestion}`, | |
| } | |
| } | |
| // For other API errors, provide context-specific messages | |
| if (error instanceof APIError) { | |
| if (error instanceof AuthenticationError) { | |
| return { | |
| valid: false, | |
| error: 'Authentication failed. Please check your API credentials.', | |
| } | |
| } | |
| if (error instanceof APIConnectionError) { | |
| return { | |
| valid: false, | |
| error: 'Network error. Please check your internet connection.', | |
| } | |
| } | |
| // Check error body for model-specific errors | |
| const errorBody = error.error as unknown | |
| if ( | |
| errorBody && | |
| typeof errorBody === 'object' && | |
| 'type' in errorBody && | |
| errorBody.type === 'not_found_error' && | |
| 'message' in errorBody && | |
| typeof errorBody.message === 'string' && | |
| errorBody.message.includes('model:') | |
| ) { | |
| return { valid: false, error: `Model '${modelName}' not found` } | |
| } | |
| // Generic API error | |
| return { valid: false, error: `API error: ${error.message}` } | |
| } | |
| // For unknown errors, be safe and reject | |
| const errorMessage = error instanceof Error ? error.message : String(error) | |
| return { | |
| valid: false, | |
| error: `Unable to validate model: ${errorMessage}`, | |
| } | |
| } | |
| // @[MODEL LAUNCH]: Add a fallback suggestion chain for the new model → previous version | |
| /** | |
| * Suggest a fallback model for 3P users when the selected model is unavailable. | |
| */ | |
| function get3PFallbackSuggestion(model: string): string | undefined { | |
| if (getAPIProvider() === 'firstParty') { | |
| return undefined | |
| } | |
| const lowerModel = model.toLowerCase() | |
| if (lowerModel.includes('opus-4-6') || lowerModel.includes('opus_4_6')) { | |
| return getModelStrings().opus41 | |
| } | |
| if (lowerModel.includes('sonnet-4-6') || lowerModel.includes('sonnet_4_6')) { | |
| return getModelStrings().sonnet45 | |
| } | |
| if (lowerModel.includes('sonnet-4-5') || lowerModel.includes('sonnet_4_5')) { | |
| return getModelStrings().sonnet40 | |
| } | |
| return undefined | |
| } | |