Checkout
A Paga-hosted payment page that takes card, bank transfer, USSD, Paga Wallet and agent payments. Choose how to open it. Everything after that works the same way.
| Environment | Checkout base URL |
|---|---|
| Sandbox | https://beta-checkout.paga.com |
| Live | https://checkout.paga.com |
How Checkout works
Start Checkout
Open the payment page with an HTML form, a payment link or JavaScript. See Choose how to start Checkout.
Your customer pays
They choose a payment method on the Paga-hosted page and complete the payment.
They return to your site
Paga redirects them to your charge_url with the result.
Paga notifies your server
Paga sends a payment notification to your callback_url.
Verify, then fulfil
Check the notification’s hash, or call Verify charge, before you deliver the order.
Try Checkout in the playground
Set the parameters, open Checkout and pay with test data, without writing any code. It runs in Sandbox, so no real money moves.
Test card. Card 5531 8866 5214 2950, expiry 09/32, CVV 555. More cards are on the Test data page.
Choose how to start Checkout
Pick the option that fits your product. The parameters, redirect, notification and verification are the same for all three.
<form method="POST">
<script
src="https://beta-checkout.paga.com/checkout/?w=150&h=40"
data-public_key="YOUR_PUBLIC_KEY"
data-amount="1000.00"
data-currency="NGN"
data-payment_reference="JHX-18743567"
data-email="[email protected]"
data-charge_url="https://yourstore.com/payment/complete"
data-callback_url="https://yourstore.com/webhooks/paga"
data-funding_sources="CARD,PAGA,TRANSFER,AGENT,USSD"
data-button_label="Make Payment">
</script>
</form>https://beta-checkout.paga.com/checkout/params?public_key=YOUR_PUBLIC_KEY&amount=1000.00¤cy=NGN&payment_reference=JHX-18743567&[email protected]&charge_url=https://yourstore.com/payment/complete&callback_url=https://yourstore.com/webhooks/paga&funding_sources=CARD,PAGA,TRANSFER,AGENT,USSD<script src="https://beta-checkout.paga.com/checkout/checkout.js"></script>
<button onclick="startPayment()">Make Payment</button>
<script>
function startPayment() {
PagaCheckout.startPayment({
public_key: "YOUR_PUBLIC_KEY",
amount: "1000.00",
currency: "NGN",
payment_reference: "JHX-18743567",
email: "[email protected]",
charge_url: "https://yourstore.com/payment/complete",
callback_url: "https://yourstore.com/webhooks/paga"
});
}
</script>Parameters
The same for all three. In the HTML form, add data- in front of each name, for example data-public_key.
All parameters (12)
| Parameter | Required | Description |
|---|---|---|
public_key | Yes | Your public key. See Get your API keys |
amount | Yes | Amount to charge, for example 1000.00 |
email | Yes | Customer’s email address |
currency | No | Defaults to NGN |
payment_reference | No | Your unique reference for the payment. Paga generates one if you leave it out |
charge_url | No | Where to send the customer after payment. Without it, they see your account’s default success page |
callback_url | No | Where Paga sends the payment notification. Set it so your server can confirm payments |
phone_number | No | Customer’s phone number |
display_image | No | A logo or image to show on the payment page |
funding_sources | No | Payment methods to offer, in order. Any of CARD, PAGA, TRANSFER, AGENT, USSD. Defaults to all |
button_label | No | HTML form only. Text on the button |
width | No | HTML form only. Button width in pixels |
After payment
Customer is redirected
To your charge_url, with charge_reference, status_code and status_message added to the URL.
Paga notifies your server
A payment notification is sent to your callback_url. This is the one to trust.
You get an email
If notifications are switched on for your business account.
https://yourstore.com/payment/complete?charge_reference=JHX-18743567&status_code=0&status_message=success
Don’t fulfil orders from the redirect aloneCustomers can change a URL. Fulfil only after you’ve verified the payment notification or called Verify charge.
Verify the payment notification
Paga sends this to your callback URL. Check its hash before you trust it, then respond with HTTP 200.
{
"statusCode": "0",
"statusMessage": "success",
"paymentReference": "Paga_Auto_Ref_20250826_132929_yjmb",
"amount": "10.00",
"currency": "NGN",
"timeStamp": "2025-08-26T13:36:04",
"description": null,
"customerEmail": "[email protected]",
"customerPhoneNumber": "+2348063334156",
"hash": "39453c520890841fe3a837701e60b7dba3f8d737696d8fa5a39e8566b9f96948eaac792e7c03783e67033c37bf6d123e1ff181f015e729e1bcfa70bd8a16ae97"
}Notification fields (10)
| Field | Description |
|---|---|
statusCode | 0 means the payment was successful |
statusMessage | Readable status, such as success |
paymentReference | Your payment reference, or the one Paga generated if you didn’t send one. Used in the hash |
amount | Amount paid, in decimal format such as 10.00. Used in the hash |
currency | Currency code, such as NGN |
timeStamp | When the payment happened, in UTC. Used in the hash |
description | Optional description. Can be null |
customerEmail | Customer’s email address, if given at checkout |
customerPhoneNumber | Customer’s phone number |
hash | SHA-512 signature to check before you trust the notification |
Check the hash
Join amount + timeStamp + paymentReference + hashKey, hash the result with SHA-512, and compare it with hash.
- Use
amountexactly as it appears in the notification, in decimal format such as10.00. - Join the values with no spaces or separators.
const crypto = require("crypto");
// body is the parsed notification
const expected = crypto
.createHash("sha512")
.update(body.amount + body.timeStamp + body.paymentReference + process.env.PAGA_HASH_KEY)
.digest("hex");
if (expected !== body.hash) return res.sendStatus(401);
// safe to fulfil the order
res.sendStatus(200);Verify charge
Confirm a payment from your server at any time, using the payment_reference. Authenticate with HTTP Basic, as in Authentication.
curl -X POST https://checkout.paga.com/checkout/transaction/verify \
-u "YOUR_PUBLIC_KEY:YOUR_SECRET_KEY" \
-H "Content-Type: application/json" \
-d '{"paymentReference": "JHX-18743567", "publicKey": "YOUR_PUBLIC_KEY", "amount": 1000, "currency": "NGN"}'{
"status_code": 0,
"status_message": "successful",
"chargeId": "JHX-18743567",
"amount": 1000,
"currency": "NGN"
}Paid. Safe to fulfil.
Pending. Check again shortly.
Invalid. The request failed validation.
Unauthorised. Check your keys.
Need help? We’re here 24/7
Talk to our support team any time, or ask questions in the developer community.
Updated about 21 hours ago

