Gestion des erreurs
L'API retourne des erreurs structurées avec des codes HTTP sémantiques et des codes d'erreur machine-readable.
Format de toutes les erreurs
json
Structure d'erreur
{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "The amount field must be at least 100.",
"details": {
"amount": ["The amount field must be at least 100."]
}
}
}
Codes HTTP
| HTTP | Signification |
|---|---|
200 | Succès — la transaction a été initiée |
400 | Requête invalide — vérifiez vos paramètres |
401 | Non authentifié — clé API manquante ou invalide |
403 | Accès refusé — scope insuffisant ou IP non autorisée |
409 | Conflit — référence dupliquée ou requête concurrente |
422 | Validation échouée — données invalides |
429 | Trop de requêtes — rate limit atteint |
502 | Erreur provider — le provider de paiement a retourné une erreur |
503 | Aucun provider disponible — essayez un autre opérateur ou pays |
Codes d'erreur applicatifs
| Code | HTTP | Description |
|---|---|---|
UNAUTHORIZED | 401 | Clé API invalide ou absente |
FORBIDDEN_SCOPE | 403 | Scope insuffisant pour cette action |
IP_NOT_ALLOWED | 403 | IP source non autorisée par la whitelist |
KEY_EXPIRED | 403 | La clé API a expiré |
VALIDATION_ERROR | 422 | Un ou plusieurs champs sont invalides |
DUPLICATE_REFERENCE | 409 | La référence marchande existe déjà |
IDEMPOTENCY_CONFLICT | 422 | Même Idempotency-Key, payload différent |
CONCURRENT_REQUEST | 409 | Requête avec cette clé déjà en cours |
PROVIDER_ERROR | 502 | Erreur retournée par le provider Mobile Money |
NO_PROVIDER_AVAILABLE | 503 | Aucun provider ne supporte cette combinaison méthode/pays |
PAYMENT_ERROR | 400 | Erreur générique de paiement |
Stratégie de retry
Certaines erreurs sont transitoires et peuvent être retentées. Voici les recommandations :
| Code HTTP | Peut être retenté ? | Recommandation |
|---|---|---|
| 429 | ✅ Oui | Respecter le header Retry-After |
| 502 | ✅ Oui | Attendre 30s, max 3 tentatives |
| 503 | ⚠️ Partiel | Essayer un autre opérateur (method) |
| 409 | ❌ Non | Ne pas retenter avec la même référence |
| 422 | ❌ Non | Corriger les paramètres avant de réessayer |
| 401 / 403 | ❌ Non | Vérifier la clé API |
php
Exemple retry avec backoff
$maxAttempts = 3;
$attempt = 0;
$retryable = [502, 503, 429];
do {
$response = Http::withHeaders([...])
->post('/api/v1/merchant/payin', $payload);
if ($response->successful()) {
break;
}
if (!in_array($response->status(), $retryable)) {
throw new \Exception($response->json('error.message'));
}
$attempt++;
sleep(min(30, pow(2, $attempt))); // exponential backoff
} while ($attempt < $maxAttempts);