decolua/9router · critical
xai discovery ${field} host ${host} is not on x.ai
Error message
xai discovery ${field} host ${host} is not on x.ai What it means
After protocol validation, the hostname must be exactly 'x.ai' or a subdomain ending in '.x.ai' (case-insensitive). Any other host is rejected, defending against lookalike/phishing domains in discovery documents that could capture authorization codes and tokens.
Source
Thrown at src/lib/oauth/services/xai.js:43
export function validateOAuthEndpoint(rawUrl, field) {
const value = String(rawUrl || "").trim();
if (!value) throw new Error(`xai discovery ${field} is empty`);
let parsed;
try {
parsed = new URL(value);
} catch (err) {
throw new Error(`xai discovery ${field} is invalid: ${err.message}`);
}
if (parsed.protocol !== "https:") {
throw new Error(`xai discovery ${field} must use https: ${value}`);
}
const host = parsed.hostname.toLowerCase().trim();
if (host !== "x.ai" && !host.endsWith(".x.ai")) {
throw new Error(`xai discovery ${field} host ${host} is not on x.ai`);
}
return value;
}
/**
* Discover authorization + token endpoints. Cached process-wide.
*/
export async function discoverEndpoints() {
if (cachedDiscovery) return cachedDiscovery;
try {
const res = await fetch(XAI_CONFIG.discoveryUrl, {
headers: { Accept: "application/json" },
});
if (res.ok) {
const data = await res.json();
cachedDiscovery = {View on GitHub (pinned to 90b52e06ff)
Solutions
- Point the field at a genuine x.ai host (https://x.ai/... or https://api.x.ai/... as applicable).
- If you route through a corporate gateway, don't override the OAuth endpoints — proxy at the network layer instead.
- Verify the discovery document was fetched over TLS from x.ai, since a foreign host here means the discovery source is wrong or compromised.
Example fix
// before XAI_TOKEN_URL=https://auth.mycompany.com/xai/token // after XAI_TOKEN_URL=https://x.ai/api/oauth/token
Defensive patterns
Strategy: validation
Validate before calling
function isXaiHost(u) {
try {
const h = new URL(String(u).trim()).hostname.toLowerCase();
return h === 'x.ai' || h.endsWith('.x.ai');
} catch { return false; }
}
if (!isXaiHost(cfg.tokenUrl)) throw new Error('xAI endpoint host must be x.ai or *.x.ai'); Type guard
function isXaiEndpoint(u) {
if (typeof u !== 'string') return false;
try {
const parsed = new URL(u.trim());
if (parsed.protocol !== 'https:') return false;
const h = parsed.hostname.toLowerCase();
return h === 'x.ai' || h.endsWith('.x.ai');
} catch { return false; }
} Prevention
- Only consume discovery documents fetched directly over TLS from x.ai.
- Never point OAuth endpoints at third-party or internal mirror domains.
- Add an allowlist check on any user/admin-supplied endpoint overrides.
When it happens
Trigger: Discovery field points at e.g. https://xai.example.com/..., https://x.ai.evil.io/... (endsWith('.x.ai') is false for this because host is 'x.ai.evil.io'), or a mirror domain like https://x-ai.com/.
Common situations: Man-in-the-middle or malicious discovery responses; teams proxying xAI through their own domain; typos in manually configured endpoints.
Related errors
- `xai discovery ${field} host ${host} is not on x.ai`
- xai discovery ${field} must use https: ${value}
- token_endpoint must be a Microsoft login endpoint
- xai discovery ${field} is invalid: ${err.message}
- xAI OAuth session not found; restart the login flow and past
AI-assisted analysis of decolua/9router@90b52e06ff (2026-08-30).
Data as JSON: /api/errors/175dcb9f4077197f.
Report an issue: GitHub.