Skip to main content
The Instant Compliance API authenticates every request with a bearer API key.

Header format

Authorization: Bearer ic_live_<32+ characters>
The key prefix (ic_live_) is fixed so secret scanners (GitHub Secret Scanning, GitGuardian, etc.) can recognise leaked keys automatically.

How keys are stored

We never store the plaintext key. At creation we keep only:
  • The first 12 characters (the prefix, for the UI label).
  • The last 4 characters (so admins can identify which key is which).
  • A SHA-256 hash of the full plaintext.
When a request arrives we hash the incoming bearer token and look it up by hash, with a constant-time comparison. The plaintext is shown exactly once at creation and never retrievable.
If you lose the plaintext key after closing the creation dialog, it is gone — there is no “show key” button. Revoke the key and issue a new one.

Issuing a key

Open Settings → Developers in Instant Compliance and click Create key. You must hold the org.api-keys permission (Administrators have it by default). You will be asked for:
  • Label — a name only used in the admin dashboard. Pick something you will recognise six months later (e.g. Zapier — HubSpot production).
  • Scopes — see below.
  • Expiry (optional) — useful for short-lived integrations or one-off scripts.

Scopes

Scopes are the public, integrator-facing surface granted to a key. Each scope maps to a backing internal permission, so a key can never exceed what the role model allows for human users.
ScopeGrants
customers:writePOST /v1/customers, PATCH /v1/customers/{id}
customers:readGET /v1/customers, GET /v1/customers/{id}
aml:readGET /v1/customers/{id}/aml
Grant the minimum scopes the integration needs. A reporting-only integration that syncs status into your CRM should ask for customers:read and aml:read only; it physically cannot write or trigger billing.

Rotation

Best practice: rotate keys every 6–12 months, and immediately on:
  • Departure of an engineer who had access to the plaintext.
  • Any suspected leak (committed to git, posted in a support ticket, etc.).
  • Decommissioning the integration.
Rotation is “create new key → cut over the integration → revoke old key”. The revoke is immediate — the next request authenticated with the revoked key returns 401 unauthorized.

IP allowlist (optional)

Keys may be locked to a list of source IPs. When set, a request from any other source is rejected at the auth layer before the scope check runs — so a stolen key from an off-allowlist source cannot even probe scopes. Useful for integrations that always call from a fixed VPC egress.

What to do if a key leaks

  1. Revoke immediately in Settings → Developers. Effect is instantaneous.
  2. Issue a fresh key for the integration.
  3. Audit the leak source and remove the secret from where it was exposed (git filter-repo, ticket scrub, etc.).
  4. Review the request log for that key to assess what was accessed.

Common errors

HTTPerror.codeCause
401unauthorizedHeader missing / malformed / wrong format / key revoked or expired
403forbidden_scopeKey authenticated but lacks the scope this route requires
See Errors for the full envelope shape.