32 — Developer
Authentication
The Finscale API authenticates every request with a Bearer secret key over TLS. Secret keys live on your servers only; publishable keys handle the one browser-facing job — initializing checkout in the browser.
Secret keys
Each account has one secret key per mode:
| Key | Mode | Moves |
|---|---|---|
sk_test_51FinscaleDemo… | Test | Test money only. Safe to use from day one. |
sk_live_•••••••••••• | Live | Real money. Issued after account activation; shown once, then redacted everywhere. |
Pass the key in the Authorization header of every request:
curl https://api.finscale.dev/v1/payments/pay_8Q2mX4nT1cVb \
-H "Authorization: Bearer sk_test_51FinscaleDemo…"
The mode of the key selects the mode of the data: a sk_test_ key sees only test payments and returns "livemode": false on every object. There is no header or flag to cross modes.
A missing or invalid key returns 401 with an authentication_error:
{
"error": {
"type": "authentication_error",
"code": "api_key_invalid",
"message": "No valid API key provided. Pass your secret key as Authorization: Bearer sk_test_…",
"request_id": "req_7Hf3kQd2"
}
}
The API is served exclusively over HTTPS. Plain-HTTP requests are refused at the edge — the key never gets a chance to leak in transit.
Never client-side
A secret key is full control of your account: it can create payments, issue refunds, and read every customer record. Treat it like a database password.
- Never ship it in browser JavaScript, mobile app binaries, or desktop clients — anything a customer can decompile or inspect.
- Never commit it to a repository, even a private one. Load it from your secret manager or environment at runtime.
- Never log it. Redact
Authorizationheaders in request logging and error trackers.
If a key does leak, rotate it immediately — and remember test keys deserve the same hygiene, since they expose real customer emails and order references from your test data.
Key rotation
Rotate keys from the Dashboard (Developers → API keys → Roll key). Rotation is zero-downtime:
-
Roll the key
Rolling issues a new secret key immediately. You choose a grace period for the old one: revoke now, in 1 hour, in 24 hours, or in 7 days.
-
Deploy the new key
Both keys authenticate during the grace period, so you deploy the replacement at your own pace — no dropped requests.
-
Old key expires
When the grace period ends, the old key returns
401 authentication_error. The Dashboard shows the last time each key was used, so you can confirm nothing still depends on it before it dies.
If a key may have leaked — a pasted log, a screen share, a departed contractor — roll it with revoke now. A minute of forced redeploy beats an attacker with write access to your payments.
Restricted keys
Today the API has two key kinds: secret and publishable. Scoped keys with per-resource permissions — a read-only key for a reconciliation worker, a refund-only key for support tooling — are on the roadmap and will appear in Developers → API keys when available. Until then, isolate services operationally: one deployment per service, secrets injected per environment, and the Dashboard's per-key usage log as your audit trail.
Publishable keys
Publishable keys (pk_test_51FinscaleDemo… / pk_live_…) are the only keys that belong in a browser. They can do exactly one thing: initialize Finscale's browser-side checkout components for a payment your server already created.
# Server side — secret key creates the payment
curl https://api.finscale.dev/v1/payments \
-H "Authorization: Bearer sk_test_51FinscaleDemo…" \
-H "Idempotency-Key: idem_ord_9f21_0716" \
-H "Content-Type: application/json" \
-d '{
"amount": 4900,
"currency": "EUR",
"payment_method": "ideal",
"reference": "ord_9f21_0716",
"return_url": "https://shop.example.com/checkout/return"
}'
# → next_action.url: "https://pay.finscale.dev/r/8Q2mX4nT"
# Browser side — send the customer to next_action.url.
# The pk_ key initializes embedded checkout fields; it cannot read or move anything.
Publishable keys can't read payments, can't refund, can't list anything. Exposing one is harmless by design — but card data still never touches your servers: the hosted checkout page collects it directly, built to PCI DSS Level 1 standards. See Security.
Key prefixes at a glance
| Prefix | Kind | Lives |
|---|---|---|
sk_test_ / sk_live_ | Secret key — full API access | Server only |
pk_test_ / pk_live_ | Publishable key — hosted checkout init | Browser-safe |
whsec_ | Webhook signing secret — verifies webhooks | Server only |