Choose an integration mode

Almost every integration question resolves once you know which credential your code carries. Pick from this table, then read the matching guide.

You are buildingCredentialGuide
A backend that calls GateAPI key (gate_sk_…)API keys
A browser app that signs users inWeb app OAuth client, authorization code + PKCEWeb app
A CLI, desktop, or mobile appNative app OAuth client (no secret) + PKCENative and CLI
A backend calling your own API as itselfMachine-to-machine OAuth clientMachine to machine
An API that receives Gate tokensNo credential — verify against JWKSVerifying tokens
An MCP server for your productProject MCP server URL — verify against JWKSMCP servers

Three things to know

Gate has three kinds of access, and each answers a different question.

API keys: your backend calls Gate. A project's API key goes in the X-API-Key header. It reads config, records usage, checks entitlements, and runs checkout. Each key has a few scopes and may be limited to one environment.

OAuth clients: people sign in to your product. Your app sends someone to Gate, they sign in, and you receive tokens that represent them. The token's sub is a Gate user id, and your API decides what that user may do. A machine-to-machine client gets short-lived tokens for your own API instead. Gate's own API does not accept these tokens, apart from the linked-accounts endpoints.

Organization roles: people use the dashboard. Members of an organization hold one of five roles that decide what they may change.

Mixing up the first two is the most common integration mistake. An API key can never represent a user, and a user's token cannot administer Gate.

What API keys cannot do

These require a real user session, because they issue credentials or change settings. An API key is refused with 403 even when it holds *:

  • every organization route, including listing and creating projects
  • updating, archiving, or restoring a project
  • creating or revoking API keys, managing OAuth clients and social login
  • connecting Stripe (PUT and PATCH /environments/{environmentId}/stripe-connection)
  • revealing a secret as a person would; a key with config:read reads values directly

Token shapes at a glance

Authorization codeClient credentialsAPI key
Access token lifetime600 s300 sUntil revoked or expired
Refresh tokenWith offline_access, 30 daysNever issuedNot applicable
RepresentsA userA clientYour backend
Verified byYour API, against JWKSYour API, against JWKSGate, on every request
Sent asAuthorization: BearerAuthorization: BearerX-API-Key

Cross-origin constraints

Browser callers must originate from an allow-listed origin. Gate hard-codes the list in src/server/origins.ts: its own GATE_BASE_URL, plus https://clippingkk.annatarhe.com, https://shelltime.xyz, https://rawback.app, https://athena.annatarhe.com, and https://athena.annatarhe.cn. This applies to both CORS on /api/v1 and better-auth's trusted origins.