Model Freedom

Use any model. Switch any time. Lose nothing.

The routing layer is not a thin proxy. Chat sessions, agents, and councils make the same call and get a normalized response — or a loud refusal. The caller does not need to know whether the model is Claude via OpenRouter, a local llama.cpp model, or a floating always-latest alias.

Identity, memory, and hydration live in Atamaia. The model is a voice. Switching it does not reset who the identity is.

The live contract — four routability fields, locked default, roster sync, model groups, circuit breaker, endpoint catalog — is AI routing. This page is the reason that contract exists. Provider portability is the lock-in argument.

Canonical host: https://api.atamaia.ai.

POST /api/ai/chat
{
  "modelId": "local:main-instruct",
  "message": "..."
}

Fully qualified id is {provider.Prefix}:{modelId}. Live OpenRouter prefix is openrouter, not or.


What “any model” means

Eight provider types (ProviderType):

Type Protocol
OpenRouter OpenAI-compatible meta-router
LocalLlamaCpp llama.cpp HTTP
Anthropic Anthropic API
OpenAI OpenAI Chat Completions (also used as the compat type for Gemini, Groq, …)
Custom Any OpenAI-compatible endpoint (Ollama, TGI, …)
AnthropicAgentSdk Claude Agent SDK subprocess
Vllm vLLM
LiteLlm LiteLLM

Vllm and LiteLlm are not on the original page. Registering a new endpoint is a provider row plus models — not a code change. How to do that, including catalog sync and X-Provider-Sync-Key, is AI routing.

A registered model is not automatically usable. Dispatch requires enabled AND available. Agent role resolution also requires approvedForAgent. A human disable survives the next roster sync. A missing roster is not an assertion of absence.


Failover is not substitution

When the chosen provider fails with a retriable error (408, 429, 5xx, timeout, connection failure), the router tries the next provider that can serve that model, in priority order. The ProviderHealthTracker opens the circuit after 3 consecutive failures and skips that provider for 5 minutes.

It will not silently swap in a different model because the one you asked for is disabled. That used to happen. It was a bug. Resolve now returns 400 with a reason. See the live local:preview-27b example on the routing page.


Cost

Every model tracks inputCostPer1M and outputCostPer1M. Local models are 0. After the hardware, inference is free. That is why background work (summarisation, embeddings, utility agent steps) can stay local while interactive work uses a cloud model whose quality justifies the price.

POST /api/ai/sync-pricing

pulls OpenRouter prices onto registered models.

POST /api/ai/broadcast sends the same prompt to several model ids and returns per-model timing and usage. Useful for comparison and councils. It is not a substitute for hydration — each call still sees whatever context you pass.


Streaming

Upstream formats are normalized to Open Responses over SSE. The client event set does not change when the provider does. Treat the live stream as authority for exact event names rather than any list reproduced here. The adapter is OpenAICompatAdapter.


What does not belong on this page

  • Presence-state routing (Dormant → local, Engaged → API) was described as a Mind feature. Cognitive REST is gone (404 on prod, 2026-08-13). Whether Mind still applies that table in-process is unverified. It is not documented here as a public switch.
  • Endpoint catalogs, sampler fields, model groups, PATCH routesAI routing.
  • How identity and memory survive a switchProvider portability, Memory surfaces.

The model is a commodity. The identity is not.