API V2 (recommended)

Authentication and response format

The API token in the Authorization header, the rate limit, the JSON format of payments and errors, and V2 HTTP status codes.

The API token#

Each merchant account has a live token (real money) and a test key (test_…, sandbox). Both are in the merchant area, under My API keys. Send either one in the Authorization header:

HTTP header, or SDK client (which sends it for you)

<?php
use Labyrinthe\LabPay\Client;

$labpay = new Client('test_xxxxxxxxxxxxxxxx'); // ou Client::fromEnv() (LABPAY_API_KEY)
  • The X-Api-Token: <token> header is also accepted.
  • Unlike V1, the token is never read from the request body or the URL (it would end up in logs).
  • A key starting with test_ puts the request in test mode; any other value is looked up among live tokens.
  • Every authenticated response carries the X-Labyrinthe-Mode: live or test header.

Missing or unknown token: 401 response with the UNAUTHENTICATED code.

401 response
{
  "message": "Token API manquant ou invalide. Envoyez-le dans l'en-tête Authorization: Bearer <token>.",
  "code": "UNAUTHENTICATED"
}

Requests#

  • Base URL: https://api.labyrinthe-rdc.com/api/V2 (uppercase V).
  • JSON body (Content-Type: application/json). V2 always answers in JSON, even without an Accept header.
  • Amounts: string or number, at most 2 decimals ("1500", "12.50", 1500). In responses, always strings with 2 decimals ("1500.00").
  • Dates: ISO 8601 (2026-11-11T10:00:00+00:00).

Rate limit#

120 requests per minute per token. Beyond that, the API answers 429 with a Retry-After header (seconds to wait).

Payment format#

Every operation (deposit, payout, refund) returns the same object, in data. It is also the content of notifications.

FieldDescription
idLabPay identifier: DEP-… (deposit), PAY-… (payout), RFD-… (refund).
referenceYour reference (optional, unique per token).
operationdeposit | payout | refund
livemodefalse for a test payment (sandbox).
statuspending, then completed or failed (see Tracking).
gateway_statusRaw LabPay status, informational (e.g. ACCEPTED, ENQUEUED).
amountDeposit: amount credited to the merchant. Payout: amount received by the recipient. Refund: amount refunded.
feeLabPay fees.
total_amountDeposit: paid by the customer. Payout: debited from the merchant balance.
currencyCurrency, 3-letter code (e.g. CDF, USD): one of the country's.
countryPhone number's country (ISO 3166-1 alpha-3, e.g. COD).
phonePhone number, in the country's local format.
providerProvider code (e.g. VODACOM_MPESA_COD).
provider_transaction_idProvider reference (the one in the customer's SMS), or null.
failure{ "code", "message" } on failure, otherwise null.
metadataYour free-form data, returned as is.
created_at, completed_atCreation; final status (null while pending).
refunded_amountDeposits only: amount already refunded or being refunded.
refunded_payment_idRefunds only: id of the refunded deposit.

Error format#

An error has the shape { "message", "code" }, plus errors (per-field messages) for a validation error. The message is in French; rely on the code (full list in Errors).

The SDKs turn these responses into typed errors (ValidationException, InsufficientBalanceError…) carrying the code, the HTTP status and the per-field errors.

422 response
{
  "message": "Le montant doit être un nombre positif avec au plus 2 décimales (ex. \"1500\" ou \"12.50\").",
  "code": "VALIDATION_ERROR",
  "errors": {
    "amount": [
      "Le montant doit être un nombre positif avec au plus 2 décimales (ex. \"1500\" ou \"12.50\")."
    ]
  }
}

HTTP status codes#

CodeMeaning
201Payment accepted, awaiting its final status.
202Unknown LabPay network response: the payment stays pending, its status is re-read automatically.
200Read, or resend of an already completed reference.
401Missing or invalid token.
403Blocked token, KYC required, live token required…
404Payment or notification not found.
409Conflict (refund already in progress, payout not cancellable…).
422Invalid data, or payment refused (data.status = failed).
429Rate limit or daily limit reached.
503Maintenance, suspended version or operation, provider closed, LabPay service unavailable (see Suspended features).

A payment refused at initiation answers 422 with the payment in data (status: "failed", failure set): it was recorded, with its id.