---
title: "Create token"
method: POST
path: "/tokens"
tags: ["tokens"]
---

# Create token

`POST /tokens`

## Request

- Base URL: `https://api.opal.dev/v1`
- URL: `https://api.opal.dev/v1/tokens`
- Auth: HTTP bearer

Creates a first-party API token. Omit `user_id` (or set it to the
caller's ID) to create a token for yourself. Set `user_id` to a service
user's ID to mint a token that authenticates as that service user.
Creating a token for another human user is not allowed.

The `signed_token` value in the response is the secret credential and is
only returned once at creation time.

## Request body

- CreateTokenInfo: Information needed to create a first-party API token.
  - `token_label` string, required: A human-readable label for the token.
  - `access_level` 'READ_ONLY' | 'FULL_ACCESS', required: The access level of an API token.
  - `user_id` string, uuid: The ID of the user the token should authenticate as. Omit or set to the caller's ID to create a personal token. Set to a service user's ID to mint a token for that service user.
  - `expires_at` string, date-time: Optional expiration time for the token.

## Response `201`

The created API token. `signed_token` is only returned on creation.

- CreateTokenResponse: The created API token. `signed_token` is the secret credential and is only returned once at creation time.
  - `token` Token, required: A first-party API token.
    - `token_id` string, uuid, required: The ID of the API token.
    - `created_at` string, date-time, required: The date and time the token was created.
    - `token_label` string, required: A human-readable label for the token.
    - `creator_user_id` string, uuid, required: The ID of the user who created the token.
    - `user_id` string, uuid, required: The ID of the user the token authenticates as.
    - `last_used_at` string, date-time, nullable: The date and time the token was last used.
    - `access_level` 'READ_ONLY' | 'FULL_ACCESS', required: The access level of an API token.
    - `expires_at` string, date-time, nullable: The date and time the token expires.
  - `signed_token` string, required: The secret token string. Store this securely; it is only returned once at creation time.

## Other responses

- `400`: Invalid request body.
- `403`: Not authorized to create this token.
- `409`: Conflict — the target service user already has the maximum number of active API tokens (2). Delete an existing token before creating another.

## Changes

- **2026-10-08** `5d8d995bc79d`: 1 info
  - endpoint added

[Operation history](https://skmtc.dev/opal/apis/opal-api/changes/tokens/post.md)

---

[API](https://skmtc.dev/opal/apis/opal-api.md) - [All operations](https://skmtc.dev/opal/apis/opal-api/llms.txt) - [OpenAPI document](https://skmtc.dev/opal/apis/opal-api/revisions/e7877ea96eab?raw)
