packages/cloud-frontend/content/authentication.mdx
import { Callout, Tabs, Cards } from "@/docs/components";
Secure your API requests with elizaOS Cloud authentication methods.
<div className="status-badge status-stable">Stable</div>elizaOS Cloud supports multiple authentication methods:
| Method | Use Case | Header / flow |
|---|---|---|
| API Key | Server-to-server | Authorization: Bearer eliza_xxx or X-API-Key |
| Session | Browser apps | Cookie-based (Steward) |
| SIWE | Wallet sign-in, get API key | GET nonce → sign message → POST verify → use key |
| Wallet header | Per-request wallet auth | X-Wallet-Address, X-Timestamp, X-Wallet-Signature |
| x402 | Crypto payments | X-PAYMENT: ... |
<Tabs items={['cURL', 'JavaScript', 'Python']}> <Tabs.Tab>
curl -X GET "https://elizacloud.ai/api/v1/dashboard" \
-H "Authorization: Bearer eliza_xxxxxxxxxxxx"
</Tabs.Tab> <Tabs.Tab>
const response = await fetch('https://elizacloud.ai/api/v1/dashboard', {
headers: {
'Authorization': 'Bearer eliza_xxxxxxxxxxxx',
},
});
</Tabs.Tab> <Tabs.Tab>
import requests
response = requests.get(
'https://elizacloud.ai/api/v1/dashboard',
headers={'Authorization': 'Bearer eliza_xxxxxxxxxxxx'}
)
</Tabs.Tab> </Tabs>
API keys use the eliza_ prefix. The same header formats work for dashboard,
server, CLI, and wallet-issued keys.
Restrict keys to specific endpoints:
{
"name": "Production Chat Key",
"permissions": [
"chat:read",
"chat:write",
"embeddings:read"
],
"rateLimit": 100
}
Permissions can be used to restrict what operations an API key can perform.
| Permission | Description |
|---|---|
chat | Chat completions |
embeddings | Generate embeddings |
images | Image generation |
video | Video generation |
voice | Voice/TTS |
knowledge | Knowledge base |
agents | Agent management |
apps | App management |
curl -X GET "https://elizacloud.ai/api/v1/api-keys" \
-H "Authorization: Bearer eliza_xxxxxxxxxxxx"
curl -X POST "https://elizacloud.ai/api/v1/api-keys/{id}/regenerate" \
-H "Authorization: Bearer eliza_xxxxxxxxxxxx"
curl -X DELETE "https://elizacloud.ai/api/v1/api-keys/{id}" \
-H "Authorization: Bearer eliza_xxxxxxxxxxxx"
For browser-based applications, sign in through Steward (hosted login). After login,
the app stores the Steward session and sets HTTP-only cookies; API calls use credentials: "include".
import { useSessionAuth } from "@/lib/hooks/use-session-auth";
function MyComponent() {
const { authenticated } = useSessionAuth();
const makeApiCall = async () => {
const response = await fetch("https://elizacloud.ai/api/v1/dashboard", {
credentials: "include",
});
};
}
Wallet-based auth supports agents and headless clients that cannot use browser sessions.
{ nonce, domain, uri, chainId, version, statement }. Nonce is one-time, 5 min TTL (Redis). Why nonce? Prevents replay; timestamp-only can be replayed within the window.{ message, signature }. Server validates domain and signature, consumes the nonce, then finds or creates user/org and returns apiKey with user and organization. New wallets get initial free credits (configurable via INITIAL_FREE_CREDITS).X-API-Key: <key> or Authorization: Bearer <key> on subsequent requests.Send on every request instead of storing an API key:
Eliza Cloud Authentication\nTimestamp: ${timestamp}\nMethod: ${method}\nPath: ${path}If the wallet is unknown, the first valid signed request creates the account (same as SIWE signup). After that, any endpoint that uses requireAuthOrApiKey accepts wallet-header auth.
POST /api/v1/topup/10, /50, /100 (x402 payment-gated):
walletAddress needed).See Wallet API for full reference, WHYs, and file list.
Pay per request with cryptocurrency:
curl -X POST "https://elizacloud.ai/api/v1/chat/completions" \
-H "Content-Type: application/json" \
-H "X-PAYMENT: <x402-payment-header>" \
-d '{"model": "gpt-4o", "messages": [...]}'
# .env.local (never commit this file)
ELIZA_API_KEY=eliza_xxxxxxxxxxxx
// Access in your code
const apiKey = process.env.ELIZA_API_KEY;
{
"error": {
"code": "UNAUTHORIZED",
"message": "Invalid or missing authentication"
}
}
Causes:
{
"error": {
"code": "FORBIDDEN",
"message": "Insufficient permissions"
}
}
Causes:
Rate limits are endpoint-specific. See Rate Limits for the current presets and retry guidance. Rate-limited responses include headers such as:
X-RateLimit-Limit: 60
X-RateLimit-Remaining: 45
X-RateLimit-Reset: 1705312860