Account

Self-service account routes for redeeming an invite, managing API keys, and exporting your data.

Operation Method Path Scope
Redeem invite POST /v1/account/invites/redeem public
List API keys GET /v1/account/api-keys account
Create API key POST /v1/account/api-keys account
Revoke API key DELETE /v1/account/api-keys/{apiKeyId} account
Export account GET /v1/account/export account

Redeem invite

Public endpoint. Trades a one-time invite token for the first API key on an account.

Request

POST /v1/account/invites/redeem
{
  "inviteToken": "<raw invite token>",
  "apiKeyName": "Customer demo CLI",
  "displayName": "Acme Demo"
}
Field Type Required Notes
inviteToken string yes Raw token from the admin invite response
apiKeyName string no Defaults to "Customer demo CLI"
displayName string no Account display name

Response: 201 Created

{
  "schemaVersion": "marrow-account-invite-redemption-v1",
  "account": { "id": "u_…", "displayName": "Acme Demo" },
  "apiKey": {
    "id": "k_…",
    "name": "Customer demo CLI",
    "scopes": ["account", "ingest", "query", "style", "evidence", "correction", "graph"],
    "rawKey": "mrr_live_…"
  }
}

The raw API key is returned once and never again. Persist it immediately.

Invite redemption is rate-limited and audited. Raw invite tokens and raw API keys are never logged; Marrow stores only a key prefix and a hash.

List API keys

GET /v1/account/api-keys
{
  "schemaVersion": "marrow-account-api-key-list-v1",
  "apiKeys": [
    {
      "id": "k_…",
      "name": "Quickstart CLI",
      "scopes": ["query", "evidence"],
      "createdAt": "…",
      "lastUsedAt": "…",
      "expiresAt": null,
      "keyPrefix": "mrr_live_abc…"
    }
  ]
}

Raw keys are never returned by list.

Create API key

POST /v1/account/api-keys
{
  "name": "Read-only query key",
  "scopes": ["query", "evidence", "style"],
  "expiresAt": "2026-12-31"
}
Field Type Required Notes
name string yes Human-readable identifier
scopes enum[] no Subset of account, ingest, query, style, evidence, correction, graph
expiresAt string no YYYY-MM-DD

Response: 201 Created

{
  "schemaVersion": "marrow-account-api-key-v1",
  "apiKey": {
    "id": "k_…",
    "name": "Read-only query key",
    "scopes": ["query", "evidence", "style"],
    "rawKey": "mrr_live_…",
    "expiresAt": "2026-12-31"
  }
}

The raw key is returned once.

Revoke API key

DELETE /v1/account/api-keys/{apiKeyId}

Returns the revoked key's metadata. Subsequent requests with that key are rejected with 401 unauthorized.

Export account

GET /v1/account/export

Returns a full JSON dump of the account's graph: notes, claims, positions, projects, entities, edges, facets, source runs, ingest jobs, style records, and API-key metadata (without raw keys). Vector values are excluded.

Admin endpoints

Operator-only endpoints sit alongside the customer ones. They use a separate bearer scheme (Authorization: Bearer <MARROW_ADMIN_TOKEN>):

Operation Method Path
Create account POST /v1/admin/accounts
Create API key POST /v1/admin/api-keys
Create invite POST /v1/admin/invites
Export account GET /v1/admin/accounts/{userId}/export
Delete account DELETE /v1/admin/accounts/{userId}?confirm=true

Admin delete cascades through API keys, rate-limit buckets, audit logs, ingest jobs, and graph rows scoped to the account.

CLI mapping

npm run dev -- api redeem-invite --invite-token <token> --api-key-name "Customer demo CLI"
npm run dev -- api api-keys
npm run dev -- api create-api-key --name "Read-only query key" --scopes query,evidence,style
npm run dev -- api revoke-api-key <api_key_id>
npm run dev -- api account-export

# Operator
npm run dev -- api admin create-account --email customer@example.com
npm run dev -- api admin create-invite --email customer@example.com --display-name "Customer Demo"
npm run dev -- api admin export-account --user-id <account_id>
npm run dev -- api admin delete-account --user-id <account_id> --yes