> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://docs.getsinbad.com/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://docs.getsinbad.com/_mcp/server.

# Authentication

> Use the partner secret on your server and the session token in your app. Sinbad checks ownership, origin, expiry and revocation on every request.

Sinbad uses two bearer credentials. Each request must use the one that matches the route.

|                 | Partner secret               | Session token                                  |
| --------------- | ---------------------------- | ---------------------------------------------- |
| Format          | `sk_…`                       | A signed token                                 |
| Used by         | Your server                  | Your customer app                              |
| Sent as         | `Authorization: Bearer sk_…` | `Authorization: Bearer <sessionToken>`         |
| `Origin` header | Rejected                     | Must match the integration's allowlist if sent |
| Access          | Your whole partner           | One customer                                   |

## Partner secret

Send the secret from your server. Partner routes reject any request that carries an `Origin` header, and a publishable `pk_` key cannot authenticate.

The secret has full access to its own partner's data: session creation and revocation, the customer directory, customer deletion, configuration, country blocks and fee drafts. Session creation and revoking a single session are limited to the integrations on the credential. There are no permission scopes.

The reference-data routes accept either credential. See [Reference data](/reference-data) and the [API reference](/api-reference) for the route list.

## Session token

Send the token on customer routes. A token belongs to one partner, integration, customer, wallet and chain, and it authorizes that customer's profile, saved accounts, offers, breakdowns, transactions and trades.

A new session lasts 86,400 seconds (24 hours). There is no refresh token: your server creates another session when needed. Sinbad checks the stored session and the current partner, integration, identity, profile and credential on every call, so an expired, revoked or invalidated token fails even if its signature is valid.

## Browser origins

If a customer request includes an `Origin` header, it must exactly match the integration's allowlist. Scheme, hostname and port all count. Paths and trailing slashes are not part of an origin. Use HTTPS, or HTTP on `localhost` or `127.0.0.1` for development.

A server or native client can omit `Origin` and still needs the session token. Browser JavaScript sends its own origin automatically. Adding an origin to the allowlist does not replace authentication.

Customer and shared routes answer `OPTIONS` preflight requests. A well-formed origin can pass preflight, but the authenticated request still checks the allowlist. The allowed request headers are `Authorization`, `Content-Type`, `Idempotency-Key`, `X-Partner-Id` and `X-Integration-Id`.

## Optional consistency headers

These headers add a mismatch check. Omit them if you do not want one, because the bearer credential already determines identity.

* `X-Partner-Id` must match the authenticated partner.
* On session creation, `X-Integration-Id` must match the `integrationId` in the body.
* On customer calls, `X-Integration-Id` must match the session's integration.

## Credential rotation and revocation

Retiring a server credential, rotating it or letting it expire stops it from authenticating new partner requests. Customer sessions that were already issued continue until they expire. If you mark a credential as compromised, Sinbad also invalidates its existing sessions.

The following also invalidate tokens: suspending a partner or integration, changing its authentication version, deleting a customer, and revoking a customer's sessions. See [Customer management](/revoke) to end one session or all of a customer's sessions.

## Verify a token

Session tokens use RS256, the type `sinbad-widget+jwt`, the audience `sinbad-widget` and the issuer `https://sinbad.app/b2b/<project-id>`. These identifiers are part of the token format.

```http
GET /v1/.well-known/jwks.json
```

The public keys let your service verify a signature and read claims such as `sub`, `puid` and `exp`. A valid signature does not prove the session is still active, because offline verification cannot see revocation. Call `GET /v1/session` to check current access.