Paiements POS (terminal physique)
Les paiements POS permettent d'envoyer un encaissement directement à un terminal physique (TPE) connecté. Le flux est synchrone : la réponse arrive lorsque le terminal traite le paiement (ou expire par timeout).
Lister les terminaux
Avant d'envoyer un paiement POS, vous devez connaître l'identifiant du terminal (poiId).
Live: GET https://aviratopayments.com/external/v1/pos/terminals?webcode={webcode}
Test: GET https://aviratopayments.com/external/v1/test/pos/terminals?webcode={webcode}Paramètres de query
| Paramètre | Type | Requis | Description |
|---|---|---|---|
webcode | string | Oui | Identifiant de votre entreprise |
syncFromProvider | boolean | Non | true pour forcer la synchronisation avec le fournisseur. Par défaut : false |
Exemple
curl -X GET "https://aviratopayments.com/external/v1/pos/terminals?webcode=SHOP01" \
-H "X-API-KEY: votre_cle_api_live"Réponse (200)
{
"success": true,
"data": [
{
"poiId": "V400m-123456789",
"status": "boarded",
"name": "Mostrador Principal",
"model": "V400m",
"createdAt": "2026-01-15T10:00:00Z",
"updatedAt": "2026-06-20T08:30:00Z"
}
]
}Seuls les terminaux à l'état boarded (actifs et opérationnels) sont renvoyés.
- Avec
syncFromProvider=false(par défaut) : renvoie tous les terminaux enregistrés commeboarded. - Avec
syncFromProvider=true: renvoie uniquement les terminaux qui sont en plus actuellement connectés (online). Utile pour savoir quels terminaux sont opérationnels en temps réel.
Environnement Test : 3 terminaux simulés sont renvoyés, tous à l'état
boarded: | poiId | Nom | Modèle | Connectivité | |-------|-----|--------|--------------| |V400m-TEST-000001| Terminal Test 1 - Mostrador | V400m | Online | |S1F2-TEST-000002| Terminal Test 2 - Terraza | S1F2 | Online | |P400Plus-TEST-000003| Terminal Test 3 - Almacen | P400Plus | Offline | AvecsyncFromProvider=true, seuls les 2 terminaux online sont renvoyés. AvecsyncFromProvider=false, les 3 le sont. Le terminal offline (P400Plus-TEST-000003) permet de tester la gestion de l'erreurDeviceError(502, code 13004) lors d'une tentative d'encaissement sur un terminal non connecté. Seuls lespoiIdde cette liste sont acceptés pour envoyer des paiements POS en Test. Utiliser unpoiIdnon listé renverra une erreur 400.
---
Créer un paiement POS
Envoie un encaissement à un terminal physique. La requête attend que le terminal traite le paiement.
Live: POST https://aviratopayments.com/external/v1/pos/payment
Test: POST https://aviratopayments.com/external/v1/test/pos/paymentParamètres du body
| Champ | Type | Requis | Description |
|---|---|---|---|
webcode | string | Oui | Identifiant de votre entreprise |
poiId | string | Oui | Identifiant du terminal (obtenu via /pos/terminals) |
amount.value | integer | Oui | Montant en centimes |
amount.currency | string | Oui | Code ISO 4217. Valeurs acceptées : EUR, GBP, USD |
description | string | Non | Description de l'encaissement. Max 255 caractères |
customReference | string | Non | Votre référence interne. Max 100 caractères |
isPreAuth | boolean | Non | true pour une préautorisation. Par défaut : false |
Exemple (Live)
curl -X POST https://aviratopayments.com/external/v1/pos/payment \
-H "X-API-KEY: votre_cle_api_live" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: pos-sale-67890" \
-d '{
"webcode": "SHOP01",
"poiId": "V400m-123456789",
"amount": {
"value": 5000,
"currency": "EUR"
},
"description": "Venta mostrador #205",
"customReference": "VENTA-205-20260628"
}'Réponse réussie (200)
{
"success": true,
"data": {
"posPaymentId": "SHOP01-POSX-1719500000",
"paymentReference": "SHOP01-POSX-1719500000",
"poiId": "V400m-123456789",
"amount": {
"value": 5000,
"currency": "EUR"
},
"status": "success",
"isPreAuth": false,
"pspReference": "KVGQSN3K2SKFNVNS",
"description": "Venta mostrador #205",
"customReference": "VENTA-205-20260628",
"createdAt": "2026-06-28 14:15:00"
}
}Format de
posPaymentId: en Live le format est{webcode}-POSX-{timestamp}. En Test le format est{webcode}-POSXT-{timestamp}.
Timeout recommandé : configurez un timeout d'au moins 240 secondes côté client HTTP et côté serveur (par exemple
max_execution_timeen PHP,proxy_read_timeoutdans Nginx, ou l'équivalent dans votre stack). La requête attend que le client interagisse avec le terminal (insérer la carte, saisir le PIN, etc.), ce qui peut prendre du temps. Si votre serveur coupe la connexion avant de recevoir la réponse, vous n'aurez pas le résultat direct — bien que le paiement puisse tout de même se finaliser en arrière-plan.
États du paiement POS
| État | Description |
|---|---|
pending | Paiement envoyé au terminal, en attente du résultat |
success | Paiement finalisé avec succès |
failed | Le paiement a échoué (refusé, erreur du terminal) |
timeout | Le terminal n'a pas répondu à temps |
Gestion des timeouts
Si le terminal ne répond pas dans le délai imparti, la réponse aura status: "timeout". Dans ce cas :
- Ne réessayez pas immédiatement : le paiement peut être en cours de traitement
- Utilisez
Idempotency-Key: si vous renvoyez la requête avec la même clé, vous recevrez la réponse stockée - Consultez l'état : utilisez
GET /pos/paymentspour vérifier si le paiement s'est finalisé - Le webhook arrive quand même : si le paiement se finalise après le timeout, vous recevrez un webhook de confirmation (
AUTHORISATION) avec le résultat final. Implémentez les webhooks comme filet de sécurité pour ne pas perdre les paiements finalisés que vous n'avez pas pu capturer dans la réponse synchrone.
Erreurs spécifiques au POS
| Code | HTTP | Cause |
|---|---|---|
| 13005 | 409 | Terminal occupé (DeviceBusy) : un autre paiement est en cours |
| 13004 | 502 | Erreur du terminal (DeviceError) : problème de communication |
| 12001 | 400 | Paramètres invalides (poiId manquant, amount incorrect, etc.) |
Toutes les erreurs POS suivent le format d'erreur standard :
{
"success": false,
"error": {
"message": "Terminal is busy processing another payment",
"code": 13005,
"statusCode": 409,
"traceId": "abc123def456..."
}
}---
Simulation POS en environnement Test
En environnement Test, les paiements POS ne sont pas envoyés à un terminal réel. Le système valide le poiId par rapport à la liste des terminaux simulés et détermine le résultat :
Terminaux simulés
Seuls les poiId renvoyés par GET /test/pos/terminals sont acceptés. Si vous envoyez un poiId qui n'est pas dans la liste, vous recevrez une erreur 400.
Si vous envoyez un paiement au terminal offline (P400Plus-TEST-000003), l'erreur réelle renvoyée par le processeur lorsqu'un terminal n'est pas connecté est simulée :
{
"success": false,
"error": {
"message": "Error in POS payment response: Reject",
"code": 13004,
"statusCode": 502,
"traceId": "..."
}
}Pour les terminaux online (V400m-TEST-000001, S1F2-TEST-000002), le résultat est déterminé par les deux derniers chiffres du montant (amount.value) :
Magic amounts (deux derniers chiffres du montant)
| Terminaison | Résultat | Description |
|---|---|---|
77 | failed | Paiement refusé (carte déclinée) |
99 | timeout | Timeout du terminal |
55 | Erreur 409 | Terminal occupé |
| Toute autre | success | Paiement réussi |
Exemples
Montant (amount.value) | Deux derniers chiffres | Résultat |
|---|---|---|
5000 (50,00 EUR) | 00 | Succès |
10077 (100,77 EUR) | 77 | Refusé |
2599 (25,99 EUR) | 99 | Timeout |
1055 (10,55 EUR) | 55 | Terminal occupé (erreur 409) |
15001 (150,01 EUR) | 01 | Succès |
Important : en Test, la réponse inclut un petit délai simulé (2 à 3 secondes) pour imiter le temps de communication avec le terminal.
Webhooks en Test : lorsqu'un paiement POS se finalise (succès ou échec) en environnement Test, un webhook simulé est généré automatiquement et envoyé à votre URL de webhook, comme en Live lorsque le processeur confirme l'opération.
---
Lister les paiements POS
Consulte l'historique des paiements POS avec filtres et pagination par curseur.
Live: GET https://aviratopayments.com/external/v1/pos/payments?webcode={webcode}
Test: GET https://aviratopayments.com/external/v1/test/pos/payments?webcode={webcode}Paramètres de query
| Paramètre | Type | Requis | Description |
|---|---|---|---|
webcode | string | Oui | Identifiant de votre entreprise |
status | string | Non | Filtrer par état : pending, success, failed, timeout |
created_at_start | string | Non | Date de début (filtre) |
created_at_end | string | Non | Date de fin (filtre) |
cursor | string | Non | Curseur de pagination (obtenu de la réponse précédente) |
take | integer | Non | Nombre de résultats par page (1-100, par défaut : 20) |
order | string | Non | Ordre des résultats : asc ou desc (par défaut : asc) |
Exemple
curl -X GET "https://aviratopayments.com/external/v1/pos/payments?webcode=SHOP01&status=success&take=10" \
-H "X-API-KEY: votre_cle_api_live"Réponse (200)
{
"success": true,
"data": {
"posPayments": [
{
"posPaymentId": "SHOP01-POSX-1719500000",
"paymentReference": "SHOP01-POSX-1719500000",
"poiId": "V400m-123456789",
"amount": { "value": 5000, "currency": "EUR" },
"status": "success",
"isPreAuth": false,
"pspReference": "KVGQSN3K2SKFNVNS",
"description": "Venta mostrador #205",
"customReference": "VENTA-205-20260628",
"createdAt": "2026-06-28 14:15:00"
}
],
"meta": {
"cursor": "eyJpZCI6NDJ9",
"hasMore": true,
"total": 156
}
}
}Pagination
La pagination utilise des curseurs plutôt que des numéros de page :
- La première requête se fait sans
cursor - Si
meta.hasMoreesttrue, utilisez la valeur demeta.cursorcomme paramètrecursordans la requête suivante - Répétez jusqu'à ce que
meta.hasMoresoitfalse
# Page 1
curl ".../pos/payments?webcode=SHOP01&take=20"
# Page 2 (en utilisant le curseur de la réponse précédente)
curl ".../pos/payments?webcode=SHOP01&take=20&cursor=eyJpZCI6NDJ9"---
Différences entre paiements en ligne et POS
| Aspect | En ligne | POS |
|---|---|---|
| Flux | Asynchrone (créer session + rediriger le client) | Synchrone (réponse immédiate du terminal) |
| Qui paie | Client dans son navigateur | Client sur le terminal physique |
| Référence | sessionId (format {webcode}-EXT-{ts}) | posPaymentId (format {webcode}-POSX-{ts}) |
| Redirection | Oui (urlOk / urlKo) | Non |
| Timeout | La session expire sur la page de paiement | Le terminal ne répond pas (état timeout) |
| Modifications | Refund, capture, cancel, extend | Refund, capture, cancel, extend (mêmes endpoints) |
| Test | Cartes fictives (holderName) | Magic amounts (deux derniers chiffres) |