musistudio/claude-code-router · error · Error

${issue.message}

Error message

${issue.message}

What it means

A connector inside a remote provider manifest failed the apiKey-target safety check: validateProviderApiKeyTarget receives a synthetic api key, the connector endpoint, the provider name and preset id, and rejects endpoints that are unsafe targets for stored credentials (e.g. credential-host mismatch). It prevents a remote manifest from exfiltrating API keys to an unrelated host.

Source

Thrown at packages/core/src/providers/manifest-service.ts:206

    ].filter((endpoint): endpoint is string => Boolean(endpoint?.trim()));
    for (const endpoint of endpoints) {
      if (/^https?:\/\//i.test(endpoint)) {
        await validatePublicHttpsUrl(endpoint, "Fetch usage URL");
        validateProviderApiKeyTarget(provider, endpoint);
      }
    }
  }
}

function validateProviderApiKeyTarget(provider: ProviderDeepLinkPayload, endpoint: string): void {
  const issue = providerEndpointCanReceiveProviderApiKey({
    apiKey: "manifest-provider-api-key",
    endpoint,
    providerName: provider.name,
    providerPresetId: findProviderPresetByBaseUrl(provider.baseUrl)?.id
  });
  if (issue) {
    throw new Error(issue.message);
  }
}

async function validatePublicHttpsUrl(value: string, label: string): Promise<void> {
  const url = new URL(providerUrlWithDefaultScheme(value));
  if (url.protocol !== "https:") {
    throw new Error(`${label} from a remote manifest must use https.`);
  }
  if (url.username || url.password) {
    throw new Error(`${label} cannot include credentials.`);
  }
  validateRemoteHostname(url.hostname, label);
  await resolveSafeAddress(url.hostname);
}

function validateRemoteHostname(hostname: string, label: string): void {
  const normalized = hostname.trim().toLowerCase().replace(/\.$/, "");
  if (!normalized) {

View on GitHub (pinned to 99f24806c6)

Solutions

  1. Make the connector endpoint use the same host (or an approved host) as the provider's baseUrl
  2. Remove the connector from the remote manifest if it does not need authenticated fetches
  3. Verify findProviderPresetByBaseUrl(provider.baseUrl) resolves to the expected preset and the endpoint matches its documented API surface
  4. Run the connector through a local manifest where API-key targeting rules are relaxed

Example fix

// before
{"account":{"connectors":[{"endpoint":"https://other-host.example/fetch"}]}}
// after
{"account":{"connectors":[{"endpoint":"https://api.myprovider.example/fetch"}]}}
Defensive patterns

Strategy: validation

Validate before calling

const issue = await validateProviderApiKeyTarget({ apiKey: 'x', endpoint: connector.endpoint, providerName: provider.name });
if (issue) throw new Error(issue.message);

Try / catch

catch (e) { if (e instanceof Error && /api key/i.test(e.message)) logManifestIssue(provider.name, e.message); }

Prevention

When it happens

Trigger: validateRemoteAccountConnector() on a connector whose endpoint does not match the provider's baseUrl/preset (findProviderPresetByBaseUrl returns a different preset, or endpoint host differs), so providerApiKeySafetyIssue/validateProviderApiKeyTarget reports an issue.

Common situations: Manifest connector endpoints pointing at a different domain than the provider base URL, connectors added for telemetry that still request the user's API key, or typos in connector endpoint URLs.

Related errors


AI-assisted analysis of musistudio/claude-code-router@99f24806c6 (2026-08-27). Data as JSON: /api/errors/dea9c09d08afe2c1. Report an issue: GitHub.