Docs · API reference

Webhooks

How miaPOS notifies your backend when a payment changes state. Signed, idempotent, retried with backoff.

AudienceDeveloper
DifficultyIntermediate
Updated2026-05-30

Overview

Webhooks are the authoritative channel for payment results. The browser redirect after checkout is for UX only — never fulfill an order based on the redirect alone. miaPOS POSTs every state change to your registered callbackUrl with a signed payload.

Payload

POST /your-callback-url HTTP/1.1
Content-Type: application/json
X-MiaPos-Signature: base64(rsa_sha256(body))
X-MiaPos-Event: payment.completed
X-MiaPos-Delivery: evt_01HZP2K7...

{
  "event":     "payment.completed",
  "paymentId": "pay_01HZP2...",
  "orderId":   "ORD-2026-00123",
  "amount":    100.00,
  "currency":  "MDL",
  "status":    "COMPLETED",
  "completedAt": "2026-05-30T14:23:45Z"
}

Verify the signature

Every webhook is signed with miaPOS' private key. Verify before trusting the payload.

  1. Read the raw request body (exact bytes — don't re-serialize).
  2. Decode the X-MiaPos-Signature header (base64).
  3. Verify with the miaPOS public key fetched from GET /ecomm/api/v1/public-key.

Full algorithm and reference code in Signature verification.

Retries and idempotency

Respond 2xx within 10 s to acknowledge. Any other response (or timeout) is retried with exponential backoff: 1m, 5m, 15m, 1h, 6h, 24h (6 attempts total over ~30 h).

Every delivery carries a unique X-MiaPos-Delivery id. Treat it as the idempotency key — store seen ids and short-circuit duplicates.

Event types

  • payment.completed — paid and settled
  • payment.failed — declined by payer's bank or scheme
  • payment.expired — TTL reached before payer acted
  • payment.refunded — full or partial refund processed