Providers
Atomic supports subscription-based providers via OAuth and API-key providers via environment variables or the auth file. Built-in catalogs ship with Atomic; configured and native providers may refresh newer catalogs independently and cache them in~/.atomic/agent/models-store.json for offline use.
Table of Contents
Subscriptions
Use/login in interactive mode, then select a provider:
- ChatGPT Plus/Pro (Codex)
- Claude Pro/Max
- GitHub Copilot
- xAI (Grok/X subscription)
- Radius
- Cursor (experimental)
Use
/logoutto clear credentials. Logout immediately invalidates authentication in the active interactive engine and removes the selected provider from both~/.atomic/agent/auth.jsonand any effective legacy~/.pi/agent/auth.json, so the provider remains logged out after restart. Environment variables, command-line credentials, andmodels.jsonconfiguration cannot be cleared by Atomic; when one of those sources still authenticates the provider, the logout status names the remaining source. Stored tokens auto-refresh when expired.
OpenAI Codex
- Requires ChatGPT Plus or Pro subscription
- Officially endorsed by OpenAI: Codex for OSS
/logout and select OpenAI ChatGPT Plus/Pro, then run /login, authenticate that subscription again, and retry the request. Atomic displays these recovery steps with the provider error; it does not automatically delete the stored credential or repeatedly retry a definitive authentication rejection.
Codex Fast Mode
Run/fast in interactive mode to enable OpenAI priority service tier separately for normal chat and workflow-stage sessions. The command is shown only when the current model scope includes a supported openai/* or openai-codex/* model. Workflow stages use the workflow setting, not the chat setting. When enabled for the active supported model, the UI appends fast after the model name in the chat footer and workflow stage model labels. Fast mode intentionally does not apply to github-copilot/*, Azure OpenAI, OpenRouter, or custom OpenAI-compatible providers. Use workflow fast mode deliberately because parallel workflow fan-out can multiply priority-tier usage.
Claude Pro/Max
Anthropic subscription auth is active for Claude Pro/Max accounts. Third-party harness usage draws from extra usage and is billed per token, not against Claude plan limits.GitHub Copilot
- Press Enter for github.com, or enter your GitHub Enterprise Server domain
- When using
COPILOT_GITHUB_TOKENinstead of/login, Atomic uses the token’sproxy-epwhen present, honorsCOPILOT_API_TARGETorGITHUB_COPILOT_BASE_URLoverrides, derives the tenant-specific GHE routing host fromGITHUB_SERVER_URL=*.ghe.com, deriveshttps://api.enterprise.githubcopilot.comfrom other non-github.comserver URLs, and otherwise falls back to the public Copilot routing hubhttps://api.githubcopilot.cominstead of the account-specific individual endpoint. - If you get “model not supported”, enable it in VS Code: Copilot Chat → model selector → select model → “Enable”
- GitHub Copilot models are populated dynamically from Copilot’s live CAPI
/modelscatalog when Copilot auth is available. Atomic synthesizes only picker-enabled, non-disabledchatentries with plain ids (for examplegithub-copilot/claude-sonnet-5andgithub-copilot/mai-code-1-flash-picker); namespaced enterprise deployments containing/are skipped rather than exposed asgithub-copilot/*models. Models that advertise long-context limits, such asgithub-copilot/gpt-5.5,github-copilot/claude-opus-4.8, andgithub-copilot/gemini-3.1-pro-preview, expose an opt-in long-context choice through--context-window, the/modelselection flow, per-modeldefaultContextWindows, SDK, and RPC controls. The long-context option advertises the model’s full context window (for example1mor1.05m— GitHub’smax_context_window_tokens), matching how the nativeopenai/*andanthropic/*providers report these models and what the chat footer shows. GitHub’s lower server-side prompt cap (max_prompt_tokens, for example936kor922k) is retained internally as the effective input budget that drives compaction thresholds and overflow recovery, and GitHub’s live output cap (max_output_tokens) replaces Atomic’s bundledmaxTokensfallback for provider requests. If CAPI advertisescapabilities.supports.reasoning_effortas an array, Atomic also gates/modeland thinking-level cycling to only those live levels for both dynamic Copilot models and bundledpi-aiCopilot models; budget-only or boolean-only reasoning metadata leaves the existing thinking map untouched. Active interactive sessions refresh from this metadata as soon as the catalog is applied, so a startup fallback model does not keep stale reasoning levels until restart. This lets Atomic display the branded context window, request the catalog-advertised output budget, and avoid offering unsupported Copilot reasoning levels. - Selecting long context sets Atomic’s displayed window to the model’s full capacity while compaction triggers against the effective prompt-token budget, and makes Copilot requests include
X-GitHub-Api-Version: 2026-06-01. Atomic does not send a body field,contextTier, or model-id variant; GitHub automatically applies the server-sidelong_contexttier when prompt tokens exceed the default budget. - Long-context Copilot requests consume more AI credits and require Copilot long-context/usage-based billing entitlement. A prompt that reaches the model’s normal prompt cap is compacted and retried automatically. Only when GitHub rejects a prompt below that cap — for example because the account lacks the long-context/usage-based billing entitlement and is dropped to a smaller server tier — does Atomic surface a friendly entitlement/server-cap/cost hint rather than silently truncating context.
- Gemini models (
github-copilot/gemini-3.1-pro-preview,github-copilot/gemini-3.5-flash, …) are served through Copilot’s CAPI gateway, which re-translates the OpenAI request into Google’s GenAI format and enforces Gemini’s stricterFunctionDeclarationschema (it rejects a tool-parameteranyOf/oneOfwhose branch is a complex object, returning400 invalid request body). Atomic automatically sanitizes outbound tool/function JSON Schemas for these models into the supported subset — resolving object/array-bearing unions to their most expressive branch, convertingconst/literal unions toenum, collapsing nullable unions tonullable, and dropping non-portable keywords such asadditionalProperties,patternProperties,format, and numeric/length bounds. Gemini also serializes array/object tool-call arguments as flattened indexed keys (keywords[0],keywords[1], …); Atomic reconstructs these back into proper arrays/objects before validation so tool calls (includingstructured_outputand MCP tools) don’t fail and loop. Both transforms are transparent and scoped to GitHub Copilot Gemini models only; no configuration is required and other providers/models are unaffected. - Claude/Anthropic Messages models served through GitHub Copilot use Copilot SSE transport. If Copilot cleanly ends a
/v1/messagesstream after Anthropic terminal stop-reason evidence but omits the requiredmessage_stopevent, Atomic adds that one terminal event before provider parsing so the turn can finish normally, including when the final complete SSE frame reaches EOF without a trailing blank-line separator. The repair covers public Copilot hosts and GHE tenant routes such ascopilot-api.<enterprise>.ghe.com, and is otherwise limited to closed, non-error Copilot Anthropic event streams; malformed, truncated, already well-formed, non-Copilot/look-alike host, non-SSE, Gemini, and OpenAI-style streams continue through the normal parser and retry behavior.
xAI (Grok/X subscription)
Run/login xai, then select Use a subscription. XAI_API_KEY remains available through Use an API key.
Radius
Radius is a dynamicpi-messages gateway. /login radius stores OAuth tokens in auth.json; its model catalog refreshes independently and is cached in models-store.json. API-key authentication is also available through /login radius or RADIUS_API_KEY. Custom Radius gateways can be declared in models.json with "oauth": "radius" and the gateway baseUrl.
Cursor (experimental)
Cursor support is bundled as the first-party@bastani/cursor extension and appears in /login as Cursor (Experimental). It uses Cursor’s browser PKCE flow and stores OAuth credentials in ~/.atomic/agent/auth.json; do not paste Cursor tokens into environment variables, command-line arguments, or custom proxies. Atomic identifies as a Cursor CLI-compatible client against private endpoints; maintainers and users should explicitly accept that this may conflict with Cursor’s terms of service, stop working without notice, or affect the Cursor account used to authenticate.
Current limitations:
- Cursor uses private, undocumented APIs and Cursor CLI-compatible headers. Atomic keeps the transport isolated and labels this provider experimental because Cursor may change the protocol without notice; use may conflict with Cursor’s terms of service or provider-side account policies.
- Image input is supported only for known multimodal Cursor Claude, Composer, Gemini, GPT, and Kimi model families (IDs beginning
claude-,composer-,gemini-,gpt-, orkimi-), plusgrok-4.3. Text-only Cursor models still reject images with a clear error. - For image-capable Cursor models, Atomic serializes user images and mixed text/image MCP tool results into Cursor’s private request format. Image payloads must be non-empty standard base64; MIME-style line wrapping whitespace is accepted and stripped before serialization.
- Model metadata is cached token-free in
~/.atomic/agent/cursor-model-catalog.jsonand can be used at startup before fresh credentials are available. Estimated labels are used only when no valid cache exists and allowed liveGetUsableModelsdiscovery failures occur; refresh-time discovery is best-effort so rotated credentials are still persisted. - Cursor’s private model discovery does not return token-limit metadata. Atomic preserves any positive limits Cursor does send, then resolves a model’s context window and max output tokens from its bundled
@earendil-works/pi-aimodel catalog by matching the Cursor model ID’s family/version. Explicit1MCursor ids or labels on any fast/thinking sibling for the same family are treated as a 1,000,000-token context floor even when the closest reference match advertises a smaller base window. Cursor-only models with no pi-ai match (for examplecomposer-*anddefault/Auto) keep a conservative 200k context / 64k output estimate. This only sets limits; it never changes which Cursor models are listed. - Cursor thinking levels are derived from the discovered variants for each model group. Atomic exposes
xhighonly when Cursor advertises anxhighormaxvariant, and exposes the distinctmaxlevel only when Cursor advertises an actualmaxvariant. If an older savedxhighormaxselection is restored for a model that currently has only lower-effort variants, the request falls back to the nearest concrete Cursor variant instead of sending an invalid id. - The implementation avoids a localhost proxy and keeps credentials OAuth-only. Cursor’s HTTP/2 transport uses the bundled
@bastani/atomic-nativesRust/N-API client, so it does not require Node.js onPATH. The native client currently opens request-scoped HTTP/2 sessions; pooling may be added in a future release. - Cursor request encoding intentionally omits a
previousWorkspaceUriscurrent-directory entry by default so local absolute working-directory paths are not sent as workspace context. HTTP/2 Connect request/framing code is isolated, buffered across arbitrary chunks, tested with injected fakes, and uses a minimal production protobuf codec with field-order-independent exec ids, protobufValueplus raw UTF-8/JSON tool arguments, historical tool-result correlation, checkpoint token-details parsing, paused-stream abort/idle cleanup, catalog-aware fast/thinking model grouping, and credential/PKCE-redacted protocol errors.
cursor/<model-id> (default: cursor/composer-2).
API Keys
Environment Variables or Auth File
Use/login in interactive mode and select a provider to store an API key in auth.json, or set credentials via environment variable:
/model without restarting Atomic, including providers with dynamically discovered catalogs.
Reference for environment variables and
auth.json keys: findEnvKeys() / getEnvApiKey() in the installed @earendil-works/pi-ai dependency (node_modules/@earendil-works/pi-ai/dist/env-api-keys.d.ts). The private provider map those functions use is in node_modules/@earendil-works/pi-ai/dist/env-api-keys.js; Atomic does not include a separate packages/ai source directory in this monorepo.
Auth File
Store credentials in~/.atomic/agent/auth.json:
0600 permissions (user read/write only). Auth file credentials take priority over environment variables.
API-key credentials may include provider-scoped env values. They take precedence over process environment variables while resolving the credential key, provider/model headers, and provider configuration such as Cloudflare account IDs, Azure settings, Vertex project/location, Bedrock settings, cache retention, and HTTP_PROXY/HTTPS_PROXY:
Key Resolution
Thekey field supports command execution, environment interpolation, and literals:
- Shell command:
"!command"at the start executes the whole value as a command and uses stdout (cached for process lifetime) - Environment interpolation:
"$ENV_VAR"or"${ENV_VAR}"uses the value of the named variable. Interpolation works inside larger literals.$FOO_BARis the variableFOO_BAR; use${FOO}_BARwhenBARis literal text. Missing environment variables make the value unresolved. - Escapes:
"$$"emits a literal"$";"$!"emits a literal"!"without triggering command execution. - Literal value: Used directly
MY_API_KEY are migrated to $MY_API_KEY on startup only when that environment variable is present during migration; otherwise the value is preserved as a literal. The same explicit $ENV_VAR rule and guarded legacy migration apply to custom provider apiKey and header values in models.json; see Custom Models. OAuth credentials are also stored here after /login and managed automatically.
Cloud Providers
Azure OpenAI
Amazon Bedrock
AWS_CONTAINER_CREDENTIALS_*) and IRSA (AWS_WEB_IDENTITY_TOKEN_FILE).
AWS_BEDROCK_FORCE_CACHE=1 to enable cache points:
Cloudflare AI Gateway
CLOUDFLARE_API_KEY can be set via /login. The account ID and gateway slug must be set as environment variables.
/compat) and prefixed model IDs (workers-ai/@cf/...). OpenAI uses the OpenAI passthrough route (/openai) with native OpenAI model IDs such as gpt-5.1. Anthropic uses the Anthropic passthrough route (/anthropic) with native Anthropic model IDs such as claude-sonnet-4-5.
AI Gateway authentication uses CLOUDFLARE_API_KEY as cf-aig-authorization. Upstream authentication can be one of:
For normal Atomic usage, prefer unified billing or stored BYOK. Inline BYOK requires configuring an additional upstream
Authorization header for the Cloudflare AI Gateway provider, for example via a models.json provider/model override.
Cloudflare Workers AI
CLOUDFLARE_API_KEY can be set via /login. CLOUDFLARE_ACCOUNT_ID must be set as an environment variable.
x-session-affinity for prefix caching discounts.
Google Vertex AI
Uses Application Default Credentials:GOOGLE_APPLICATION_CREDENTIALS to a service account key file.
llama.cpp
For router-mode discovery, load/unload management, and Hugging Face downloads with a local llama.cpp server, see llama.cpp. Configure it with/login llama.cpp or LLAMA_BASE_URL and manage models with /llama.
Custom Providers
Via models.json: Add Ollama, LM Studio, vLLM, or any provider that speaks a supported API (OpenAI Completions, OpenAI Responses, Anthropic Messages, Google Generative AI). See Custom models. Via extensions: For providers that need custom API implementations or OAuth flows, create an extension. See Custom providers and examples/extensions/custom-provider-gitlab-duo.Resolution Order
When resolving credentials for a provider:- CLI
--api-keyflag auth.jsonentry (API key or OAuth token)- Environment variable
- Custom provider keys from
models.json