Self — the caller's user + tenant + session context
const url = 'https://example.com/v1/identity/whoami';const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
try { const response = await fetch(url, options); const data = await response.json(); console.log(data);} catch (error) { console.error(error);}curl --request GET \ --url https://example.com/v1/identity/whoami \ --header 'Authorization: Bearer <token>'Reflects the auth middleware’s attached context: tenantId + scopes always; userId / sessionId / providerId / expiresAt when the caller is on a session token; the fuller UserRecord under user when a userId is present and the IdentityDirectoryBinding resolves it. Always mounted — the /users/* routes only mount when the directory binding is wired.
Authorizations
Section titled “Authorizations”Responses
Section titled “Responses”Auth + user context.
Introspection of the caller’s current authentication context. Always carries tenantId and scopes (empty for static bearer tokens), plus userId when the token carries one; principal says whom the caller acts as, and an API key adds tokenId, its role and the projectId it is limited to; session-token callers additionally see sessionId, providerId, and expiresAt. user is the caller’s directory record, present when the deployment wires an identity directory and it knows the userId. reviewerRole is set when the caller is a reviewer — its token carries a reviewer role, or its user is a registered reviewer — so clients can gate reviewer-only UI (the approvals surface) without a second round trip.
object
The caller as approvals name a person: user:<id> or service_account:<id>, the same string as an approval’s requestedBy and a decision’s decidedBy.
Reviewer role class. Hierarchy: standard < senior < admin.
Tenant-scoped user record (admin plane). primaryEmail may be redacted on the wire based on tenant policy (the routes treat it as opaque). metadata is free-form JSON — deployments carry IdP claims / provisioning source / roles here.
object
When they were removed from the tenant (POST /v1/identity/users/{userId}/unregister); absent while they are here.
object
The person’s grants: only on GET /v1/identity/users?include=grants, and only from a runtime that reads grants.
object
Whether the person is a tenant admin. Absent when the runtime has no authorization store: nothing grants it then.
Whether the person is a tenant member: they read the tenant’s settings (providers, policies, adapters, signing keys, deployments), not its projects. A person is one from being added. Absent when the runtime has no authorization store, or doesn’t report it.
Direct project memberships.
A person’s direct role on a project.
object
Role on a project, as read. member is only read, on a role given before it was retired: it grants what viewer does, and writes refuse it.
Team memberships.
A person’s role in a team.
object
Role on a team membership.
A person’s active entry on the reviewer roster.
object
Reviewer role class. Hierarchy: standard < senior < admin.
Whom an API key acts for: a person, or a service account.
object
The user id, or the service account id.
The caller’s API key, when it is one.
The caller’s API key role, when the key has one.
The project the caller’s API key is limited to, when it is.
Whether the caller is a tenant admin, decided as the admin routes decide it: admin on the tenant when the runtime authorizes, otherwise the tenant-admin scope of a full key (never a member key or one limited to a project). A console shows its admin pages by it. Absent from older servers: read scopes.
Example
{ "reviewerRole": "standard", "user": { "grants": { "projects": [ { "role": "viewer" } ], "teams": [ { "role": "member" } ], "reviewer": { "role": "standard" } } }, "principal": { "kind": "user" }, "role": "admin"}Missing / malformed / expired / revoked bearer token.
object
object
Stable machine-readable discriminant. Values match domain error codes (see docs/API-ROUTE-CONVENTIONS.md §4.3).
Optional, kind-specific.
object
Server-assigned request id; also echoed via X-Request-Id header.
Examplegenerated
{ "error": { "code": "example", "message": "example", "details": {}, "requestId": "example" }}