Documentation Index Fetch the complete documentation index at: https://docs.voight.xyz/llms.txt
Use this file to discover all available pages before exploring further.
All /me/* endpoints require a Privy JWT (the dashboard auth token). The frontend handles this for you — these docs are for if you’re building external tools that talk to your own Voight account.
Authentication
Authorization: Bearer <privy-jwt>
Get the JWT from your browser’s dev tools while logged into the dashboard:
// In the browser console at voight.xyz/dashboard
const { getAccessToken } = window . __privy
console . log ( await getAccessToken ())
JWTs expire in ~1 hour. Long-running scripts should re-fetch periodically. For programmatic / long-lived access, use an API key on /v1/events for ingestion or build a separate backend that signs Privy JWTs server-side.
Identity + profile
Method Path Purpose GET/meCurrent user (id, privyId, email, wallet, handle) PATCH/meUpdate handle
curl -H "Authorization: Bearer $JWT " https://voight-production.up.railway.app/v1/me
Agents
Method Path Purpose GET/me/agentsList all your agents GET/me/agents/:idFull agent profile + 30-day calendar + KPIs + recent sessions / errors PATCH/me/agents/:idEdit displayName DELETE/me/agents/:idSoft-delete agent + block ingestion (returns 410 Gone going forward)
curl -H "Authorization: Bearer $JWT " \
https://voight-production.up.railway.app/v1/me/agents
Events
Method Path Purpose GET/me/events?limit=N&since=24h|7d|30d|all&agentId=cuidStream of recent events (cap 1000)
Query params (all optional):
Param Default Notes limit50 Clamped 1..1000 since(none) 24h, 7d, 30d, all. Invalid values silently dropped.agentId(none) Filter by one agent. Must be a CUID. Non-CUID values silently dropped.
curl -H "Authorization: Bearer $JWT " \
"https://voight-production.up.railway.app/v1/me/events?limit=100&since=24h"
Sessions
Method Path Purpose GET/me/sessions?limit=NAggregated sessions (grouped by sessionId) GET/me/sessions/:idOne session detail with all events
Traces
Method Path Purpose GET/me/traces?since=XTraces (grouped by metadata.traceId) GET/me/traces/:traceIdOne trace with full timeline + git context + privacy chips
Errors
Method Path Purpose GET/me/errors?since=XError clusters (Sentry-style, grouped by fingerprint) POST/me/errors/:fingerprint/resolveMark cluster resolved DELETE/me/errors/:fingerprint/resolveRe-open cluster
Clusters auto-reopen if a new event matches the fingerprint with timestamp > resolvedAt.
Alerts
Method Path Purpose GET/me/alerts?status=X&count=YActive / acknowledged / all alerts POST/me/alerts/:id/acknowledgeAck alert POST/me/alerts/:id/snoozeSnooze N hours (?hours=24) POST/me/alerts/:id/unacknowledgeRe-open alert
API keys
Method Path Purpose GET/me/keysYour API keys (prefix + label + lastUsedAt) POST/me/keysCreate a new key. Returns the plaintext once . DELETE/me/keys/:idRevoke a key
# Create
curl -X POST -H "Authorization: Bearer $JWT " \
-H "content-type: application/json" \
-d '{"label":"My production bot"}' \
https://voight-production.up.railway.app/v1/me/keys
# Response (only time you'll see the secret)
# { "id": "...", "keyPrefix": "vk_abc12345", "secret": "vk_abc12345...full key...", "label": "My production bot" }
Spend summary
Method Path Purpose GET/me/spend-summaryAggregated cost across all your agents (used by Overview KPI)
Returns { total, by_agent: [...], by_model: [...], by_day: [...] }.
Test event
Method Path Purpose POST/me/test-eventCreate a synthetic event for onboarding/testing. Creates a placeholder agent if needed.
curl -X POST -H "Authorization: Bearer $JWT " \
https://voight-production.up.railway.app/v1/me/test-event
The synthetic agent has isPublic: false and a recognizable ownerWallet (voight:test:<userId>) so it won’t appear on the public Explorer.
Rate limits
Per-user, per-endpoint. Reasonable defaults — if you hit a 429, back off. If you need higher limits for a specific use case, reach out .
Notes
All /me/* endpoints filter by userId server-side. Cross-user reads are impossible from the API.
Soft-deleted agents are filtered out of all reads (deletedAt: null filter). The 9 read queries that touch Agent enforce this; the mutation queries (alert ack/snooze) intentionally keep the filter absent so you can dismiss alerts for deleted agents.
Endpoint behavior is documented in source at apps/api/src/routes/me.ts .
Next
POST /v1/events Event ingestion (API key auth, not JWT).
Public agents Read-only Explorer endpoints (no auth).