musistudio/claude-code-router · error · Error
OpenRouter providers request failed (${response.status}): ${
Error message
OpenRouter providers request failed (${response.status}): ${text.slice(0, 200)} What it means
getOpenRouterProviderCatalog fetches `${apiRoot}/api/v1/providers` (or a model endpoints path) and throws when the HTTP response is not ok, including status and first 200 chars of the body. This is the primary failure point for OpenRouter catalog discovery when the API is unreachable, rate-limited, or returns an error.
Source
Thrown at packages/core/src/providers/openrouter-provider-catalog.ts:33
const apiRoot = openRouterApiRoot(request.baseUrl);
const model = stringValue(request.model);
const cacheKey = model ? `${apiRoot}:model:${model}` : `${apiRoot}:providers`;
const cached = providerCache.get(cacheKey);
const now = Date.now();
if (cached && now - cached.fetchedAt < providerCacheTtlMs) {
return {
loadedFrom: apiRoot,
providers: cached.providers
};
}
const endpointPath = model
? modelEndpointsPath(model)
: "/api/v1/providers";
const response = await fetch(`${trimRight(apiRoot, "/")}${endpointPath}`);
if (!response.ok) {
const text = await response.text().catch(() => "");
throw new Error(`OpenRouter providers request failed (${response.status}): ${text.slice(0, 200)}`);
}
const payload = await response.json() as unknown;
const record = isRecord(payload) ? payload : {};
const data = model && isRecord(record.data) && Array.isArray(record.data.endpoints)
? record.data.endpoints
: Array.isArray(record.data)
? record.data
: [];
const providers = model
? mergeProviderActivity(
normalizeOpenRouterEndpointProviders(data),
await loadYesterdayProviderTokenTotals(apiRoot, apiKey, model)
)
: normalizeOpenRouterProviders(data);
providerCache.set(cacheKey, { fetchedAt: now, providers });
return {
loadedFrom: apiRoot,View on GitHub (pinned to 99f24806c6)
Solutions
- Check the status code in the message: 429 → back off and retry with caching; 404 → fix apiRoot (should be the OpenRouter site root, not /api/v1); 401/403 → check proxy/auth requirements
- Cache catalog results and refresh infrequently instead of on every call
- Retry with exponential backoff for 5xx/429 since these are transient
- Verify the endpoint still exists in the current OpenRouter docs if 404 persists
Example fix
// before
const catalog = await getOpenRouterProviderCatalog({ apiRoot: "https://openrouter.ai/api/v1" });
// after
const catalog = await getOpenRouterProviderCatalog({ apiRoot: "https://openrouter.ai" }); Defensive patterns
Strategy: retry
Validate before calling
if (!/^https:\/\/openrouter\.ai/.test(apiRoot)) throw new Error('apiRoot should be the OpenRouter site root'); Try / catch
catch (e) { if (e instanceof Error && /OpenRouter providers request failed \((429|5\d\d)\)/.test(e.message)) return await withBackoff(() => getOpenRouterProviderCatalog(opts)); throw e; } Prevention
- Cache catalog results with a TTL
- Back off on 429/5xx instead of immediate retries
- Pin apiRoot to the documented site root
When it happens
Trigger: fetch to the OpenRouter API root returning non-2xx: 401/403 (auth or wrong apiRoot), 404 (wrong apiRoot or endpoint moved), 429 (rate limit), 5xx (outage), or a proxy/gateway error page.
Common situations: Misconfigured apiRoot (pointing at the model endpoint base instead of the site root), OpenRouter deprecating endpoints, corporate proxies returning 407/502, or hitting rate limits while polling the catalog repeatedly.
Understand the failure class
Background: 'Something went wrong' / 'Request failed (500)' / 'HTTP error! status: 404' — what failed HTTP requests actually mean and how to find the real cause — this error's family across 28 libraries.
Related errors
- OpenRouter endpoints request timed out after ${endpointFetch
- ZCode profiles can only open the app; agent arguments are no
- Claude Design profiles can only be opened from CCR Desktop.
- Claude App profiles do not support agent arguments.
- HTTP + response.status + from CCR remote sync
AI-assisted analysis of musistudio/claude-code-router@99f24806c6 (2026-08-27).
Data as JSON: /api/errors/b3ef3efc66e576c9.
Report an issue: GitHub.