API reference navigation
POST /v1/keys

Mint an API key

Access
Authenticated
keys:create
Cost
Free
Rate limit
20 / minute per account
Quota
None

Create a scoped API key. The entitlements must be a subset of what you can grant (your own capabilities intersected with the plan). An optional per-key credit cap ceilings its monthly spend. The plaintext secret is returned exactly once in this response and is never retrievable again.

Request body MintKeyRequest

  • label string required

    Your own name for the key, for finding it later.

    max 200 chars
  • entitlements array of string required

    What the key may do. Must be a subset of what YOU can grant, which is your own capabilities intersected with the plan’s; asking for more is a 403.

    max 38 items
  • creditCap integer

    A per-period spending ceiling for this key. Omit for uncapped. A capped key that runs out is refused with a 429 and cannot drain the account.

    min 0
  • requireSignature boolean

    Require an RFC 9421 signature on every request this key makes. Sending this without `publicKeyJwk` is a 400, since it would create a key that could never authenticate.

  • publicKeyJwk Ed25519PublicJwk

    An Ed25519 public JWK to register as this key’s first signer.

    • kty string required

      Key type. Must be `OKP`; anything else is rejected with a 400.

      OKP
    • crv string required

      Curve. Must be `Ed25519`; no other algorithm is accepted.

      Ed25519
    • x string required

      The base64url-encoded Ed25519 public key. Public material only — never send a private key.

      max 64 chars

Responses

  • 200 The new key and its one-time secret
    • id string required

      The key id. Stable across rotations: rotating changes the secret, never the id.

    • label string required

      Your own name for the key.

    • credentialKind string required

      What kind of credential this is.

    • status string required

      Whether the key is live or revoked.

    • requireSignature boolean required

      When true, every request from this key must carry a valid RFC 9421 HTTP message signature; an unsigned request is rejected with a 401. Enforcement is per key, not global.

    • entitlements array of string required

      Exactly what this key may do. Always a subset of what its creator could grant, so a key can never exceed the person or key that minted it. Changing it takes effect on the very next request, with no grace window.

    • createdByKind string required

      Whether a member or another key created this one.

    • createdById string required

      The member id or key id that created it.

    • createdAt string required

      When the key was created, as an ISO 8601 instant.

    • revokedAt string | null required

      When the key was revoked, as an ISO 8601 instant. Null while live. Revocation is immediate and irreversible.

    • lastUsedAt string | null required

      When the key was last seen on a request, as an ISO 8601 instant. Null means it has never been used, which is how you find keys safe to revoke.

    • secrets array of KeySecretView required

      The live secrets on this key, masked. Two are present during a rotation grace window.

      • prefixHint string required

        The leading, non-secret part of the key string, for recognising it.

      • last4 string required

        The last four characters, for distinguishing two keys at a glance.

      • display string required

        The masked form to show a user. Safe to log and display; it is not the credential.

      • createdAt string required

        When this secret was minted, as an ISO 8601 instant.

      • expiresAt string | null required

        When this secret stops resolving, as an ISO 8601 instant. Set on a secret retired by a rotation, during its grace window. Null on the current secret.

    • creditCap integer | null required

      A ceiling on what this key may spend per period. Null means uncapped. A key that hits its cap is refused with a 429 until the period rolls over, which contains a runaway agent without touching the rest of the account.

    • monthSpent integer required

      Credits this key has spent in the current period, measured against `creditCap`.

    • secret string required

      The plaintext key. Returned EXACTLY ONCE, here, and never retrievable again — store it now or rotate the key to get a new one.

    • signerThumbprint string | null required

      The RFC 7638 thumbprint of the registered signer, which is the `keyid` your signatures must carry. Null when no JWK was supplied.

  • 401 No or invalid credential
    • code string required

      Stable machine-readable error code. Branch on this, never on the numeric status.

      bad_requestunauthorizedsignature_requiredpayment_requiredforbiddennot_foundconflictgonepayload_too_largeunprocessable_entitytoo_many_requestsinternal_errornot_implementedbilling_unavailablenot_contactablemailbox_link_unavailablemailbox_requiredmail_engine_unavailablewebhook_publisher_unavailabledatabase_unavailableclient_error
    • message string required

      Human-readable explanation of the refusal.

    • status integer required

      The HTTP status code, repeated in the body.

    • remedy object

      A self-serve path forward, when one exists (a 402 points at the credit top-up).

      • kind string required

        What kind of remedy this is, so a client can route it: whether the caller can clear the condition through the API, or a person must act in the web app.

        topupconnect_mailbox
      • url string required

        Where to go to clear the condition: an API path, or a web app page when only a person can.

  • 402 Plan does not include API keys
    • code string required

      Stable machine-readable error code. Branch on this, never on the numeric status.

      bad_requestunauthorizedsignature_requiredpayment_requiredforbiddennot_foundconflictgonepayload_too_largeunprocessable_entitytoo_many_requestsinternal_errornot_implementedbilling_unavailablenot_contactablemailbox_link_unavailablemailbox_requiredmail_engine_unavailablewebhook_publisher_unavailabledatabase_unavailableclient_error
    • message string required

      Human-readable explanation of the refusal.

    • status integer required

      The HTTP status code, repeated in the body.

    • remedy object

      A self-serve path forward, when one exists (a 402 points at the credit top-up).

      • kind string required

        What kind of remedy this is, so a client can route it: whether the caller can clear the condition through the API, or a person must act in the web app.

        topupconnect_mailbox
      • url string required

        Where to go to clear the condition: an API path, or a web app page when only a person can.

  • 403 Missing keys:create, or entitlements you cannot grant
    • code string required

      Stable machine-readable error code. Branch on this, never on the numeric status.

      bad_requestunauthorizedsignature_requiredpayment_requiredforbiddennot_foundconflictgonepayload_too_largeunprocessable_entitytoo_many_requestsinternal_errornot_implementedbilling_unavailablenot_contactablemailbox_link_unavailablemailbox_requiredmail_engine_unavailablewebhook_publisher_unavailabledatabase_unavailableclient_error
    • message string required

      Human-readable explanation of the refusal.

    • status integer required

      The HTTP status code, repeated in the body.

    • remedy object

      A self-serve path forward, when one exists (a 402 points at the credit top-up).

      • kind string required

        What kind of remedy this is, so a client can route it: whether the caller can clear the condition through the API, or a person must act in the web app.

        topupconnect_mailbox
      • url string required

        Where to go to clear the condition: an API path, or a web app page when only a person can.