> ## Documentation Index
> Fetch the complete documentation index at: https://docs.wellapp.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# ApiKey

> ApiKey represents a long-lived programmatic credential scoped to a workspace (and optionally to a specific person/member) that authenticates API requests via th

ApiKey represents a long-lived programmatic credential scoped to a workspace (and optionally to a specific person/member) that authenticates API requests via the `ApiKeyStrategy` in the auth chain. It is created by workspace members through the `POST /v1/api-keys` endpoint and revoked via `DELETE /v1/api-keys/:id`; no PATCH route exists. Each key is linked to one or more workspace connectors via a separate `api_key_workspace_connector_links` join table, and those connectors are cleaned up automatically on revocation. The `value` field is the raw bearer secret — it is only surfaced once at creation; all subsequent list responses return a `masked_key` derived from it.

| Naming                          | Value                             |
| ------------------------------- | --------------------------------- |
| Object                          | ApiKey                            |
| Resource type (JSON:API `type`) | `api_key`                         |
| Collection / records root       | — <sub>(not a records root)</sub> |
| REST base                       | `/v1/api-key`                     |
| Entity class                    | `ApiKey`                          |

<Note>
  **Internal object.** Not currently exposed on the public REST API. The operations below describe the intended contract.
</Note>

## API operations

| Operation | Method & path             | Status     |
| --------- | ------------------------- | ---------- |
| List      | `GET /v1/api-key`         | 🟡 Planned |
| Retrieve  | `GET /v1/api-key/{id}`    | 🟡 Planned |
| Create    | `POST /v1/api-key`        | 🟡 Planned |
| Update    | `PATCH /v1/api-key/{id}`  | 🟡 Planned |
| Delete    | `DELETE /v1/api-key/{id}` | 🟡 Planned |

## Data model

### Attributes

| Field            | Type                      | Required | Constraints                                                                 | Allowed values | Description                                                                                                                                                                                  |
| ---------------- | ------------------------- | -------- | --------------------------------------------------------------------------- | -------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| api\_key\_id     | string (UUID) — 🔒 system | ✅ Yes    | unique; defaultRaw: gen\_random\_uuid()                                     | —              | Public stable identifier for the API key. Used as the JSON:API `id` and in all API routes (`:id` param). Generated by the database on INSERT.                                                |
| value            | string — 🔒 system        | ✅ Yes    | unique; varchar(255)                                                        | —              | The raw bearer secret. Generated server-side by ApiKeyService at creation; never surfaced again after the creation response. List and GET responses return `masked_key` instead.             |
| name             | string                    | ✅ Yes    | varchar(255); not null                                                      | —              | Human-readable label for the key, supplied by the caller at creation (e.g. 'CI Pipeline Key').                                                                                               |
| created\_at      | datetime — 🔒 system      | ✅ Yes    | timestamptz; not null; set on INSERT via onCreate hook                      | —              | Timestamp of key creation, set automatically by the MikroORM `onCreate` lifecycle hook.                                                                                                      |
| updated\_at      | datetime — 🔒 system      | ⚪ No     | timestamptz; nullable; set on INSERT and UPDATE via onCreate/onUpdate hooks | —              | Timestamp of last modification, managed by MikroORM lifecycle hooks.                                                                                                                         |
| last\_used\_at   | datetime — 🔒 system      | ⚪ No     | timestamptz; nullable                                                       | —              | Timestamp of the last successful authentication using this key, stamped by ApiKeyStrategy at each successful auth pass.                                                                      |
| expiration\_date | datetime                  | ⚪ No     | timestamptz; nullable                                                       | —              | Optional expiry date-time after which the key should be considered invalid. Supplied as `expiration_at` in the creation payload. No server-side expiry enforcement beyond this stored value. |
| is\_active       | boolean                   | ✅ Yes    | not null; default true                                                      | true, false    | Soft-disable flag. Set to false by ApiKeyService.revokeApiKey() on DELETE. Keys with is\_active=false are rejected by ApiKeyStrategy.                                                        |

### Relationships

| Name      | Type               | Required            | Description                                                                                                                                              |
| --------- | ------------------ | ------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------- |
| workspace | to-one (ManyToOne) | No (nullable: true) | The workspace this API key is scoped to. Set at creation; required at the business-logic level (controller throws 400 if absent). Target: Workspace.     |
| people    | to-one (ManyToOne) | No (nullable: true) | The person (workspace member) who created the key, resolved from the Firebase membership at creation time. Null for system-created keys. Target: People. |

### System-computed

* api\_key\_id — generated via gen\_random\_uuid() defaultRaw on INSERT
* created\_at — set by MikroORM onCreate hook, never writable
* updated\_at — set by MikroORM onCreate + onUpdate hooks, never writable
* value — generated server-side by ApiKeyService (random secure secret); returned once at creation, never again
* last\_used\_at — stamped by ApiKeyStrategy on each successful auth pass, not user-writable
* is\_active — defaults to true on INSERT; set to false by ApiKeyService.revokeApiKey() on DELETE, not directly patchable

## Example

```json theme={null}
{
  "data": {
    "type": "api_key",
    "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
    "attributes": {
      "name": "CI Pipeline Key",
      "is_active": true,
      "created_at": "2026-01-15T09:00:00.000Z",
      "last_used_at": "2026-05-28T14:32:11.000Z",
      "expiration_at": "2027-01-15T09:00:00.000Z",
      "masked_key": "sk_live_ab...ef12"
    }
  }
}
```

<sub>Source: `apps/api/src/database/entities/ApiKey.ts` · domain: platform · tier: Platform</sub>
