---
title: "Get a secret"
method: GET
path: "/api/secrets/{id}"
---

# Get a secret

`GET /api/secrets/{id}`

## Request

- Base URL: `https://api.hyperbrowser.ai`
- URL: `https://api.hyperbrowser.ai/api/secrets/{id}`
- Auth: API key in header `x-api-key`
- TypeScript: <https://skmtc.dev/hyperbrowser/apis/hyperbrowser-api/docs/api/secrets/:id/get.ts> (a function with typed inputs; its response is checked against the schema)

Returns a secret and its stored versions. Values are never returned. Secrets are enabled for teams on request; please contact support to enable them (otherwise 403 SECRETS_FEATURE_DISABLED). Restricted API keys need the secrets.read scope. When you're signed in rather than using an API key, you must be a team owner or admin (otherwise 403 SECRETS_ADMIN_REQUIRED).

## Path parameters

- `id` string, uuid, required

## Response `200`

Success

- SecretDetail: A secret. The API never returns its value.
  - `id` string, uuid, required
  - `name` string, required: 1-128 letters, digits, `_` or `-`, starting with a letter or digit. Unique within your team.
  - `description` string, required
  - `type` 'secret' | 'totp' | 'op_token', required: What the value is. Fixed at creation. `secret`: any string, set as an environment variable and, once it has allowed origins, typed into browser pages. `totp`: an authenticator seed (base32, or an `otpauth://totp/` URI); environment variables get the code current when the process starts, and fills type the code current at fill time. `op_token`: a 1Password service account token, used only to read the `onePassword` fields of a sandbox create, process start or browser credential fill; it's never an environment variable, a vault entry or a value typed into a page. Treat types you don't recognize as opaque: more may be added.
  - `metadata` SecretMetadata, required: Settings that aren't secret, returned by the API and editable without uploading a new value. A `secret` or `totp` secret can't be filled into browser pages until `browser.allowedOrigins` is set. An `op_token` secret accepts only `{}` (otherwise 400 SECRET_METADATA_INVALID).
    - `browser` SecretBrowserMetadata: Where the secret may be typed into browser pages. Allowed for `secret` and `totp`.
      - `allowedOrigins` string[], required: Origins a page or frame must be on before anything is typed, as `scheme://host[:port]` with no path, such as `https://github.com`. A leading `*.` matches any subdomain but not the domain itself, and must name at least two labels (`*.example.com`); you can't use a wildcard with an IP address. Origins must use https, except `http://localhost`, `http://127.0.0.1` and `http://[::1]`. Hyperbrowser lowercases origins, drops default ports and removes duplicates. An invalid entry returns 400 SECRET_METADATA_INVALID naming it.
  - `encryptionContext` string, required: Copy this verbatim into the `ctx` header of every envelope you upload for this secret. Don't build it yourself: it includes the secret's type for types other than `secret`, and an envelope sealed with another context returns 400 SECRET_ENVELOPE_INVALID.
  - `latestVersion` integer, nullable, required: The newest version number, or null until a value is uploaded.
  - `createdAt` string, date-time, required
  - `updatedAt` string, date-time, required
  - `protection` 'platform' | 'customer': `platform` (the default): the value is encrypted to the platform key. `customer`: each version is also wrapped with your own key, and each use passes the envelope you unwrapped. See [Customer-protected secrets](/sandboxes/customer-keys).
  - `versions` SecretVersion[], required: Stored versions, newest first. Values are never returned.
    - `version` integer, required
    - `kid` string, required: ID of the platform public key the envelope (for a customer-protected secret, the inner envelope) was encrypted to.
    - `createdAt` string, date-time, required
    - `outerKid` string: Customer-protected secrets only: the ID of your key that wrapped this version.
    - `retiresAt` string, date-time, nullable: When the platform key this version was encrypted to is retired. Uses after then fail with 409 SECRET_KEY_RETIRED; add a new version. Null when no retirement is scheduled.

## Other responses

- `400`: Invalid secret ID.
- `401`: Authentication required.
- `403`: API_KEY_SCOPE_DENIED (the API key lacks a required scope), SECRETS_FEATURE_DISABLED, or SECRETS_ADMIN_REQUIRED.
- `404`: SECRET_NOT_FOUND: no secret with this ID in your team.
- `500`: Internal server error.

## Changes

- **2026-11-10** `94dc06948680`: 3 info
  - added the optional property `allOf[#/components/schemas/Secret]/protection` to the response with the `200` status
  - added the optional property `allOf[subschema #2]/versions/items/outerKid` to the response with the `200` status
  - added the optional property `allOf[subschema #2]/versions/items/retiresAt` to the response with the `200` status
- **2026-10-15** `6ca0b00ee564`: 1 info
  - endpoint added

[Operation history](https://skmtc.dev/hyperbrowser/apis/hyperbrowser-api/changes/api/secrets/:id/get.md)

---

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