Authentication
Pzero has two non-interchangeable auth modes. Use the right one for each surface.
| Mode | Credential | Used for |
|---|---|---|
| Session | HttpOnly pzero_session cookie (SIWE) | /v1/account/*, /v1/x402/top-up, /v1/supply/*, /auth/* |
| Bearer | Authorization: Bearer pzero_… | POST /v1/chat/completions |
| Public | none | /healthz, /v1/models, /v1/market/*, /v1/supply/pool/summary, /auth/nonce |
Hard rules: a session cookie on the inference endpoint is rejected (401), and a Bearer key on account or supply mutations is rejected. The wallet address always comes from server-side session context, never from the client.
SIWE session (web and headless)
bash
# 1. Nonce
curl "${PUBLIC_URL}/auth/nonce?walletAddress=0xYourWallet"
# 2. Sign the EIP-4361 message for the site domain on chain 8453, then verify
curl -X POST "${PUBLIC_URL}/auth/verify" \
-H "Content-Type: application/json" \
-c cookies.txt \
-d '{"message":"<full SIWE message>","signature":"0x..."}'
# → Set-Cookie: pzero_session=...The SIWE domain must match the deployment host, and chainId must be 8453 (Base).
Bearer keys for inference
Create a key from your account (POST /v1/account/api-keys), then send it on completions:
bash
curl -X POST "${PUBLIC_URL}/v1/chat/completions" \
-H "Authorization: Bearer pzero_..." \
-H "Content-Type: application/json" \
-d '{ "model": "llama-3.3-70b", "messages": [...] }'Keys are shown once at creation and can be revoked individually.
Headless agent flow
- SIWE:
GET /auth/nonce→ sign →POST /auth/verify(store the cookie). - Fund:
POST /v1/x402/top-up(402 → sign EIP-3009 → retry). See x402 top-up. - Create a Bearer key:
POST /v1/account/api-keys. - Call
POST /v1/chat/completionswith the Bearer key.