linshenkx/prompt-optimizer · error · APIError
API error: ${JSON.stringify(error.response.data)}
Error message
API error: ${JSON.stringify(error.response.data)} What it means
The OpenAI-compatible request failed and the error carried an axios-style error.response.data payload (a structured provider error body). The adapter JSON-stringifies that body into the APIError message so the provider's error detail (code, message) is preserved.
Source
Thrown at packages/core/src/services/llm/adapters/openai-adapter.ts:183
throw new APIError('Unexpected API response format')
} catch (error: any) {
console.error('[OpenAIAdapter] Failed to fetch models:', error)
// 连接错误处理(包括跨域检测)
if (error.message && (error.message.includes('Failed to fetch') ||
error.message.includes('Connection error'))) {
const isCrossOriginError = this.detectCrossOriginError(error, baseURL)
if (isCrossOriginError) {
throw new APIError(`Cross-origin connection failed: ${error.message}`)
} else {
throw new APIError(`Connection failed: ${error.message}`)
}
}
// API返回的错误信息
if (error.response?.data) {
throw new APIError(`API error: ${JSON.stringify(error.response.data)}`)
}
// 其他错误,保持原始信息
throw new APIError(error.message || 'Unknown error')
}
}
// ===== 参数定义(用于buildDefaultModel) =====
/**
* 获取参数定义
* 基于 OpenAI 官方文档: https://platform.openai.com/docs/api-reference/chat/create
*/
protected getParameterDefinitions(_modelId: string): readonly ParameterDefinition[] {
return [
{
name: 'reasoning_effort',
labelKey: 'params.reasoning_effort.label',View on GitHub (pinned to 3e677b1d9f)
Solutions
- Read the embedded JSON: code/message fields identify the exact provider error
- invalid_api_key → fix connectionConfig.apiKey
- model_not_found → update the model ID in config
- 429/quota → retry with backoff and check billing limits
Example fix
// before
catch (e) { console.log(e.message) } // opaque JSON string
// after
catch (e: any) {
const m = /API error: (.*)$/.exec(e.message)
const detail = m ? JSON.parse(m[1]) : null
if (detail?.code === 'invalid_api_key') refreshKey()
} Defensive patterns
Strategy: try-catch
Validate before calling
null
Type guard
function parseProviderApiError(e: unknown): { code?: string; message?: string } | null {
if (!(e instanceof APIError)) return null
const m = /API error: (.*)$/.exec(e.message)
try { return m ? JSON.parse(m[1]) : null } catch { return null }
} Try / catch
try { await adapter.getModelsAsync() }
catch (e) {
const detail = parseProviderApiError(e)
if (detail?.code === 'invalid_api_key') return rotateKey()
if (detail?.code === 'rate_limit_exceeded') return backoffRetry(fn)
throw e
} Prevention
- Parse the embedded JSON instead of string-matching
- Rotate keys automatically on 401
- Set billing/quota alerts on provider dashboards
When it happens
Trigger: Provider returned 4xx/5xx with a JSON error body: invalid API key, model not found, insufficient quota, context length exceeded — surfaced during getModelsAsync.
Common situations: 401 invalid_api_key, 404 model_not_found after renaming, 429 rate_limit_exceeded, billing/quota exhausted on OpenAI or a compatible gateway.
Related errors
- GENERATION_FAILED
- GENERATION_FAILED
- UNSUPPORTED_TEST_TYPE
- API returned empty model list
- Anthropic API error (${error.status}): ${error.message}
AI-assisted analysis of linshenkx/prompt-optimizer@3e677b1d9f (2026-08-27).
Data as JSON: /api/errors/c0f5ba176d62f759.
Report an issue: GitHub.