Postbacks

We post these to the Callback URL on your Payment Profile. environment is SANDBOX for payments through a sandbox Payment Profile, which are simulated: nothing was charged.

Verify Webhooks

You are able to verify that a webhook has been received from an authorised source. All webhooks you receive will have 2 additional headers, signature and application-key.

Obtaining the secret

You can go into the API Settings on the Payment Profile, and you will be able to see a "Callback secret", if you want to generate a new webhook secret, you can click the refresh icon.

Verifying the signature

$computedSignature = hash_hmac('sha256', file_get_contents('php://input'), $configuredSigningSecret);

Payments

actWhen
sms_payment_startedWe've texted the customer asking them to confirm.
sms_payment_completedThe customer has paid.
sms_payment_failedThe payment didn't go through; see failure_reason.
sms_payment_expiredThe customer didn't reply in time.

Amounts are in pence. See Payment Request for every status and failure_reason.

{
    "act": "sms_payment_completed",
    "environment": "LIVE",
    "payment_id": 845,
    "payment_uuid": "5e2d8c1a-7b3f-4d9e-a0c6-1f2e3d4c5b6a",
    "payment_request_id": 1201,
    "payment_request_uuid": "9d41a2c6-2f0e-4c8a-9a51-2b7f0c3e8d14",
    "reference_id": "123456",
    "options": "optional string",
    "status": "COMPLETED",
    "amount": 1500,
    "currency": "GBP",
    "product": {
        "product_uuid": "0b7a9e2c-6d4f-4a1b-8c3e-5f6a7b8c9d0e",
        "name": "Chat credit",
        "billing_type": "ONE_OFF"
    },
    "msisdn": "447700900123",
    "network": "UK.O2",
    "failure_reason": null,
    "completed_at": "2026-11-06T10:15:42+00:00",
    "subscription_uuid": null
}

subscription_uuid is set when the first payment for a subscription product completes.

Subscriptions

actWhen
sms_subscription_renewedA renewal was charged.
sms_subscription_renewal_failedA renewal failed and is being retried. Sent once per run of failures.
sms_subscription_cancelledThe customer replied STOP, you cancelled it, or the retries ran out.

charge describes the renewal the postback is about, and is null on sms_subscription_cancelled.

{
    "act": "sms_subscription_renewed",
    "environment": "LIVE",
    "subscription_id": 312,
    "subscription_uuid": "4c1e0f7a-3b2d-4e8f-a6c9-0d1e2f3a4b5c",
    "payment_uuid": "5e2d8c1a-7b3f-4d9e-a0c6-1f2e3d4c5b6a",
    "payment_request_id": 1201,
    "payment_request_uuid": "9d41a2c6-2f0e-4c8a-9a51-2b7f0c3e8d14",
    "reference_id": "123456",
    "options": "optional string",
    "status": "ACTIVE",
    "product": {
        "product_uuid": "0b7a9e2c-6d4f-4a1b-8c3e-5f6a7b8c9d0e",
        "name": "VIP chat",
        "billing_type": "SUBSCRIPTION"
    },
    "msisdn": "447700900123",
    "network": "UK.O2",
    "renewal_amount": 1000,
    "renewal_period_days": 30,
    "renewal_period_minutes": null,
    "currency": "GBP",
    "renewals": 3,
    "next_charge_at": "2027-01-01T09:00:12+00:00",
    "cancel_reason": null,
    "cancelled_at": null,
    "charge": {
        "charge_id": 2290,
        "amount": 1000,
        "status": "SUCCEEDED",
        "failure_reason": null,
        "completed_at": "2026-12-01T09:00:40+00:00"
    }
}