Integrate
Authentication
Every API request carries two credentials. Keep both on your server.
| Header | Value | Identifies |
|---|---|---|
X-API-Key |
pk_ + 64 hex characters |
The application |
Authorization |
Bearer + access token |
Your organization |
Send Accept: application/json too, and Content-Type: application/json with a body.
curl https://pay.fanak.ly/api/v1/payment-intents/4d893346-bd5e-482f-8347-3f509a877f1a \ -H "X-API-Key: $FANAK_API_KEY" \ -H "Authorization: Bearer $FANAK_ACCESS_TOKEN" \ -H "Accept: application/json"use Illuminate\Http\Client\PendingRequest;use Illuminate\Support\Facades\Http;
function fanak(): PendingRequest{ return Http::baseUrl('https://pay.fanak.ly/api/v1') ->withHeaders(['X-API-Key' => config('services.fanak.api_key')]) ->withToken(config('services.fanak.access_token')) ->acceptJson();}
$intent = fanak()->get('payment-intents/4d893346-bd5e-482f-8347-3f509a877f1a')->throw()->json('data');async function fanak(path, init = {}) { const response = await fetch(`https://pay.fanak.ly/api/v1/${path}`, { ...init, headers: { 'X-API-Key': process.env.FANAK_API_KEY, Authorization: `Bearer ${process.env.FANAK_ACCESS_TOKEN}`, Accept: 'application/json', 'Content-Type': 'application/json', ...init.headers, }, });
if (!response.ok) { throw new Error(`Fanak answered ${response.status}: ${await response.text()}`); }
return (await response.json()).data;}
const intent = await fanak('payment-intents/4d893346-bd5e-482f-8347-3f509a877f1a');How the two credentials fit together
Section titled “How the two credentials fit together”- One access token works with the API key of every application in your organization.
- The API key must belong to an active application of that organization.
- Another application’s intent returns
403, even in your organization.
Getting your credentials
Section titled “Getting your credentials”Owners and developers manage them in the dashboard.
| Credential | Where |
|---|---|
API key (pk_...) |
Applications → roll the API key |
Webhook secret (whsec_...) |
Applications → roll the webhook secret (webhooks) |
| Access token | Access tokens → create |
Each value is shown once; Fanak keeps only a hash of the API key.
Replacing a credential
Section titled “Replacing a credential”| Credential | How |
|---|---|
| API key | Rolling stops the old key at once (401). Deploy right after. |
| Webhook secret | Applies at once. See Secret rotation. |
| Access token | Create, deploy, then revoke the old one. |
When authentication fails
Section titled “When authentication fails”The API answers 401:
| Problem | Response body |
|---|---|
| Missing, invalid, revoked or expired token | {"message": "Unauthenticated."} |
Missing X-API-Key |
{"error": "Missing X-API-Key header."} |
| Unknown key, another organization’s key, inactive application | {"error": "Invalid API key or inactive application."} |