🟢 xAI OAuth Onboarding
Use any active
xAI account — X Premium, X Premium+, SuperGrok, or SuperGrok Heavy — for
,
,
and multi-agent models. No separate API key needed.
This is standard OAuth 2.0 (RFC 8628 Device Authorization Grant), not a vendor-custom flow.
Tier → model access
The JWT issued by
carries a
claim; higher tiers unlock more models from
. Observed mapping (xAI does not publish this officially):
| Tier | Subscription | Approx. model access |
|---|
| 1 | X Premium ($8/mo) | grok-4.3 baseline |
| 2 | X Premium+ ($16/mo) | + grok-4.20-0309 variants |
| 3 | SuperGrok ($30/mo) | + reasoning models |
| 4 | SuperGrok Heavy ($300/mo) | + grok-build-0.1 + multi-agent |
reports the user's tier so they know which models will be available.
This is a
script-mode skill — no tools registered. Read this file, then call the exports from a
block.
See also
- skill — for vendor-key BYOK setup (xAI API key from console.x.ai, different mechanism — bills per-token, NOT subscription-backed)
- skill — same pattern, for ChatGPT/Codex subscription
config/context/references/model-onboarding.md
— overall model-selection landscape
When to use this skill
✅ Use when the user EXPLICITLY says one of:
- "Sign in with my Grok / SuperGrok account"
- "Use my SuperGrok / X Premium subscription"
- "Connect SuperGrok Heavy"
- "Login with xAI / Grok"
- "Use my Grok Heavy subscription"
❌ Do NOT use for:
- "Add Grok via API key" / "I have an xAI API key" → use (the xAI template)
- Other vendors (Anthropic, OpenAI, Gemini, Qwen, etc.) → use
- "Add the Grok model" without subscription mention → ASK the user which path they want (subscription OAuth vs. API key BYOK)
The two paths are mutually exclusive billing-wise. Subscription OAuth uses the user's monthly quota; BYOK API key uses console.x.ai pay-per-token credits.
Critical preflight — account gate awareness
xAI has a known backend gate that denies OAuth grants for some accounts even with an active SuperGrok subscription. This is upstream xAI behavior, not a client bug. Symptoms:
- Verification page loads, but clicking "Approve" returns from the token endpoint
- Hermes Agent has documented the same in issue #26847
- Verify the user's SuperGrok subscription is active (grok.com / settings)
- Suggest they try the verification URL in their already-logged-in browser (not a fresh incognito)
- If still denied → fall back to BYOK API key path ( skill, xAI template, key from https://console.x.ai)
Do NOT silently retry — the gate is deterministic per account, retrying wastes time.
Flow
The flow has 4 user-visible steps. Drive it like this:
1. start() — generate the verification URL
bash
python3 - <<'EOF'
import json, sys
sys.path.insert(0, '/data/workspace/skills/xai-grok-onboarding')
from exports import start
print(json.dumps(start(), indent=2))
EOF
Returns
verification_url_with_code
— tell the user to open it in their browser, log in (if needed), and click Approve.
⚠️ Wait for explicit user confirmation before calling poll(). Polling too eagerly burns tokens for a "still pending" state.
2. poll() — confirm approval (after the user says "done")
bash
python3 - <<'EOF'
import json, sys
sys.path.insert(0, '/data/workspace/skills/xai-grok-onboarding')
from exports import poll
print(json.dumps(poll(), indent=2))
EOF
Three terminal outcomes:
- → success; show the user to switch to
- → user hasn't approved yet; ask them to confirm before re-polling
- with → see "account gate" section above
- with → device code timed out (15 min); call again
3. After successful connect — tell the user
The frontend model picker refreshes after connect. The default model is
. Other available models depend on the subscription tier (SuperGrok Heavy unlocks
).
To switch:
or use the picker.
Function reference
| Function | Args | Returns |
|---|
| — | Current credential state + available models + expiry |
| — | Device code prompt: {verification_url_with_code, user_code, expires_in_seconds}
|
| optional | {status: connected/pending}
+ credential info |
| — | Delete credential + flush agent cache |
| — | Force-refresh access token (debug; normally automatic) |
| — | List available models from the OAuth endpoint |
on
bypasses the cache TTL.
All functions return a dict with
on success or
on failure.
After connecting
Models surface with the
prefix:
- — primary chat model (default)
- — Grok Build coding model (SuperGrok Heavy tier only)
xai-grok/grok-4.20-0309-reasoning
— reasoning variant
xai-grok/grok-4.20-0309-non-reasoning
— faster, no reasoning
xai-grok/grok-4.20-multi-agent-0309
— multi-agent variant (uses /v1/responses internally)
User switches via
or the model picker UI.
Lane routing (transparent)
The provider auto-routes based on model id:
- Multi-agent models →
https://api.x.ai/v1/responses
(Responses API)
- All other Grok models →
https://api.x.ai/v1/chat/completions
(OpenAI-compatible)
Users do not need to know which dialect each model speaks — passing the standard
shape works for both. For multi-agent, an optional
thinking={"effort": "low"|"medium"|"high"}
controls how many agents collaborate.
Subsequent chat calls hit
directly using the OAuth bearer — bypasses the platform proxy.
Subscription usage limits apply (not the platform credit balance). Image / video models (
) are filtered out of the chat picker but accessible via image generation tools.
Limits & BYOK fallback
xAI does not publish exact daily caps or RPM the way OpenAI does. Practical reality for OAuth-backed Grok usage:
- No published hard numbers. Limits are fair-use based — xAI throttles temporarily if you generate massive volume in a short window.
- Tier matters. Heavy ($300/mo) gives the highest consumer ceiling — significantly above SuperGrok ($30) or X Premium+. Standard text/chat rarely hits the cap for normal-to-heavy daily use.
- Image / video / voice have tighter quotas. E.g. Heavy users get roughly ~80+ video generations per 12 hours, but these can still throttle during peak load.
- Soft ceiling signal: if the user starts seeing or "rate limit exceeded" messages from xAI, they've hit the fair-use ceiling for that feature. Wait it out (limits reset on a rolling window, not a fixed daily clock) or switch billing modes.
When to suggest switching to BYOK
If the user wants predictable, spend-based high-volume access — or if they're hitting limits often — they can switch to a regular xAI API key:
- Get a key at https://console.x.ai (pay-per-token, separate from subscription)
- Use skill with the xAI template
- BYOK models appear alongside OAuth models in the picker — switch per turn
Both paths can coexist; the user picks per request. OAuth = subscription quota (good default). BYOK = clearer rate limits + per-token billing (good for heavy automation or when you want cost transparency).
Error → action table
| Symptom | Cause | Action |
|---|
| / "rate limit exceeded" on chat | OAuth fair-use ceiling hit | Wait for soft reset, or switch this request to BYOK |
| / at OAuth time | xAI account gated | Use BYOK (see preflight section above) |
| Repeated after | Token revoked / subscription canceled | + restart, or switch to BYOK |
| / 5xx upstream | xAI infra issue | Retry shortly. BYOK uses the same upstream, won't help |
Reauth
Tokens auto-refresh via
(6h access token TTL — relatively generous vs Codex's 1h). If a 401 surfaces:
- — try the manual refresh path
- If still failing, + restart from
Critical rules
- Never paste user_code into the verification URL field for the user. The URL
accounts.x.ai/oauth2/device?user_code=XXXX
already embeds the code — just open it.
- Never start the flow without explicit user request. "I want to use Grok" needs a follow-up question about subscription vs. API key; "use my SuperGrok subscription" is enough.
- Wait for user confirmation between and . Auto-polling wastes API calls and produces stale "pending" responses.
- On , do NOT retry blindly. Explain the gate, suggest BYOK fallback.
- Never log or echo the access_token / refresh_token. They're persistent credentials. The exports never include them in return values either.