Skip to content
/api/v1/user/

Get the authenticated user's profile, API key, and embedded subscription state.

Get the authenticated user's profile, API key, and embedded subscription state. EXEMPT (`cost: 0`). JWT auth required.

Why use this

Authenticated 'who am I?' probe — returns full user profile plus embedded subscription (`Userplan`), document-quota (`UserDocumentLimit`), and device-limit (`UserDeviceLimit`) relationship rows. EXEMPT (`cost: 0`). Identical shape to the `user` field in the /auth/login response (both invoke `User.to_dict(include_relations=True)`). Use to bootstrap dashboard state on app load — the JWT cookie is presumed valid; if it expired the endpoint returns 401 and the SPA should redirect to /auth/login. Includes `api_key` (32-char) for the dashboard's 'API Keys' page; the user's `credit_balance` (USD top-up wallet, NOT tokens); subscription `plan` (`free` / `weekly` / `monthly` / `pro` / `yearly`); and notification preferences (`webhook_url`, `notify_email`, `notify_browser`).

Common use case

Dashboard SPA bootstraps on load by calling this endpoint to populate user state. Server-side automation should never call this — use the user's `api_key` directly for billed endpoints, no profile fetch needed.

Authenticated 'who am I?' endpoint — returns the full user profile plus embedded Userplan / UserDocumentLimit / UserDeviceLimit relationship rows. EXEMPT (cost: 0). The dashboard SPA calls this on app load to bootstrap user state; server-side automation should NOT — use the api_key directly. Note the response is identical in shape to the user field in the POST /api/v1/auth/login response (both invoke to_dict(include_relations=True)). To update notification preferences (webhook_url, notify_email, notify_browser) use PUT /api/v1/user/; for the live token balance use GET /api/v1/account/balance; for subscription details use GET /api/v1/billing/subscription.

Response schema

FieldTypeNullableDescription
userobjectnoAuthenticated user profile (matches the `user` field in the /auth/login response). Built by `User.to_dict(include_relations=True)` — includes the three relationship rows (`Userplan`, `UserDocumentLimit`, `UserDeviceLimit`) inline.
user.uuidstringnoStable user identifier (UUIDv4 string). Foreign-key target in every per-user table; treat as the canonical user PK.
user.emailstringnoLowercased registration email. Unique across `users`. Used as the login identifier.
user.usertypestringnoRole enum value — `user` (default) or `admin`. Use to gate admin-only UI surfaces. Distinct from `billing_admin` (a finer-grained flag for billing-operator dashboard access).
user.api_keystringnoAPI key for server-to-server billed calls (32-char concatenation of two UUIDs with hyphens removed). Pass as `X-API-Key: <api_key>` header on `/api/v1/sec/*`, `/api/insiders/*`, etc. Distinct from the JWT `token` (issued by /auth/login) — JWT is for browsing the dashboard, API key is for server-to-server calls.
user.verify_emailbooleannoTrue if the user has clicked the verification email link. Always true here — login is gated by this flag, so the JWT bearer must already be verified.
user.has_uat_accessbooleannoTrue if the user is allowed onto the UAT environment (separate cohort gate from the production access flag). Use to render UAT-environment banners or to gate UAT-only feature flags.
user.billing_adminbooleannoPhase 56-02 RBAC flag — true if the user can access the billing-operator dashboard (`/admin/billing/*` routes). Distinct from `usertype === 'admin'` (which grants full admin access).
user.credit_balancenumbernoStripe-paid top-up balance in USD (not in cents). Used by [POST /api/v1/billing/quota](/docs/account/billing-and-subscription/post-billing-quota) for buying additional API quota at 100 requests / $1. NOT the same as the token balance (see [GET /api/v1/account/balance](/docs/account/token-pricing/get-account-balance) for that).
user.webhook_urlstringyesUser-configured HTTPS URL for sniper-hit webhook callbacks. Null when the user has not configured one (most users). PUT /api/v1/user/ with `webhook_url` to update.
user.notify_emailbooleannoTrue if email notifications are enabled. Default true. Toggle via PUT /api/v1/user/.
user.notify_browserbooleannoTrue if in-browser push notifications are enabled. Default true. Toggle via PUT /api/v1/user/.
user.created_atstringnoISO-8601 UTC timestamp the user account was created (set by /auth/register).
user.updated_atstringnoISO-8601 UTC timestamp the user row was last modified (`onupdate=datetime.utcnow`). Bumped on profile edits, login (last-seen), and admin role changes.
user.UserplanobjectyesEmbedded subscription state — `total_limit_api` (monthly request quota), `reach_limit_api` (consumed this cycle), `plan` (`free`/`weekly`/`monthly`/`pro`/`yearly`), `status` (`active`/`canceled`/`past_due`), `current_period_end`. Null in legacy edge cases where the relationship row was never seeded; /auth/register seeds this for new users.
user.UserDocumentLimitobjectyesEmbedded document-quota state for the (legacy) RAG document-upload feature — `total_limit_GB` and `reach_limit_GB`. Most users do not consume document quota.
user.UserDeviceLimitobjectyesEmbedded device-limit state — `device_limit` (max concurrent JWT sessions, default 2) and `user_login_device` (JSON-serialized array of active session_ids). When a third login lands the oldest session_id is evicted from the array.

Sample response

·
  • "user":
    • "id": 42
    • "uuid": "0f14ed05-3a2e-4b76-9c11-1a7c8b3f6de2"
    • "email": "user@example.com"
    • "usertype": "user"
    • "api_key": "a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6"
    • "verify_email": true
    • "is_online": true
    • "has_uat_access": false
    • "billing_admin": false
    • "credit_balance": 12.5
    • "notify_email": true
    • "notify_browser": true
    • "webhook_url": "https://your-app.example.com/webhooks/finradar"
    • "created_at": "2026-04-15T10:00:00.000Z"
    • "updated_at": "2026-05-02T15:51:00.000Z"
    • "Userplan":
    • "UserDocumentLimit":
    • "UserDeviceLimit":
    }
}

Errors

StatusLabelDescription
200OKRequest succeeded.
400Bad RequestInvalid query, body, or path parameter.
401UnauthorizedMissing or invalid Authorization header / api_Token.
402Payment RequiredInsufficient token balance for this call. Top up
429Too Many RequestsRate limit exceeded for your tier (see /pricing for tier limits). Tier limits
500Server ErrorUnexpected server-side failure. Retry with backoff; report if persistent.

Code samples

curl "https://api.finradar.ai/api/v1/user/" \
  -H "Authorization: Bearer YOUR_JWT_TOKEN"

Generate an API key in /account/credentials to run live queries (literal YOUR_API_KEY placeholder shown until then).