Authentication
All Gatelithix API requests require authentication via API keys passed as Bearer tokens.
API Key Types
| Key Type | Prefix | Usage |
|---|---|---|
| Secret key (test) | sk_test_ | Server-side sandbox requests |
| Secret key (live) | sk_live_ | Server-side production requests |
| Publishable key (test) | pk_test_ | Client-side tokenization (sandbox) |
| Publishable key (live) | pk_live_ | Client-side tokenization (production) |
Secret keys can perform all API operations. Never expose them in client-side code, browser JavaScript, or version control.
Publishable keys are restricted to tokenization operations. They are safe to use in browser-side hosted fields and mobile apps.
Environment Modes
Keys with _test_ in the prefix operate in sandbox mode. Test transactions are processed against simulated connectors and never charge real cards.
Keys with _live_ in the prefix operate in production mode. Live transactions are routed to real payment processors.
Development Mode (DEV_MODE)
When running locally with make dev, the gateway starts with DEV_MODE=true. In this mode:
- Authentication is bypassed — all requests are treated as authenticated with a test merchant identity
- A sandbox connector is seeded — payments route to the built-in simulator
- No API keys are required — you can call any endpoint without an Authorization header
This lets you test the full payment flow without setting up Auth0 or creating API keys. DEV_MODE is automatically disabled in production.
Warning: DEV_MODE must never be used in production. The gateway includes a safety guard that prevents
DEV_MODE=truein Cloud Run environments.
Bearer Token Usage
Pass your API key in the Authorization header as a Bearer token:
Authorization: Bearer sk_test_aBcDeFgHiJkLmNoPqRsTuVwXEvery API request without a valid Authorization header returns a 401 error with authentication_required code.
API Key Management
Create an API Key
The full plaintext key is returned only once in the creation response. Store it securely.
List API Keys
curl https://sandbox.api.gatelithix.com/v1/api-keys \
-H "Authorization: Bearer sk_test_your_key_here"Returns all keys for the merchant. The plaintext key is never included in list responses.
Rotate an API Key
curl -X POST https://sandbox.api.gatelithix.com/v1/api-keys/{keyID}/rotate \
-H "Authorization: Bearer sk_test_your_key_here" \
-H "Idempotency-Key: rot_$(uuidgen)"Generates a new key value while preserving the key ID, name, and scopes. The old key is immediately invalidated.
Revoke an API Key
curl -X DELETE https://sandbox.api.gatelithix.com/v1/api-keys/{keyID} \
-H "Authorization: Bearer sk_test_your_key_here"Permanently deactivates the key. Revoked keys return invalid_api_key on any subsequent request.
Idempotency
All POST write endpoints require an Idempotency-Key header. This ensures that retrying a request (e.g., due to a network timeout) does not create duplicate operations.
Idempotency-Key: unique-request-id-hereRules:
- Same key with same parameters returns the cached response.
- Same key with different parameters returns a
422 idempotency_param_mismatcherror. - Concurrent requests with the same key return a
409 idempotency_conflicterror. - Idempotency keys expire after 72 hours.
Use a UUID or other unique identifier for each distinct operation.
Selecting a connector account
As of v2.3, every charge the gateway settles is bound to a specific
per-merchant connector_account. See
Connector Accounts for the full model. At request
time, callers may optionally pick which account handles the charge via
either of:
| Carrier | Name | Pattern | Notes |
|---|---|---|---|
| Body field | connector_account | ^ca_[a-z0-9]{10}$ | Preferred for most SDKs. |
| Header | X-Connector-Account | ^ca_[a-z0-9]{10}$ | Equivalent — useful for middleware that cannot edit the body. |
Precedence — body wins. If both the body connector_account and
X-Connector-Account header are set:
- If they are equal, the request proceeds normally.
- If they disagree, the gateway returns
400 connector_account_ambiguous.
When it is required. The connector_account selector is optional
when the merchant has exactly one active account for the routed
(connector, mode, key_kind) triple (the gateway auto-picks the default).
It is required when the merchant has more than one active account for
that triple — otherwise the gateway returns
400 connector_account_required.
Example using the body field:
curl -X POST https://sandbox.api.gatelithix.com/v1/payments/authorize \
-H "Authorization: Bearer sk_test_your_key_here" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: auth_$(uuidgen)" \
-d '{
"amount": 5000,
"currency": "usd",
"gateway_token": "tok_test_aBcDeFgHiJkLmNoPqRsTuVwX",
"connector_account": "ca_abc123def4"
}'Equivalent using the header:
curl -X POST https://sandbox.api.gatelithix.com/v1/payments/authorize \
-H "Authorization: Bearer sk_test_your_key_here" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: auth_$(uuidgen)" \
-H "X-Connector-Account: ca_abc123def4" \
-d '{
"amount": 5000,
"currency": "usd",
"gateway_token": "tok_test_aBcDeFgHiJkLmNoPqRsTuVwX"
}'Capture, refund, and void must settle through the same account the
originating authorize / sale used. A differing connector_account on a
follow-on operation returns 400 connector_account_override_forbidden.