On every payment confirmation we get from the payment provider, we send the following to your webhook with us. First lets define the fields
Field | Description |
---|---|
status | This is the status of the payment. this can be success or failed or refunded in the case of payment refunds |
clientId | This is your clientId |
amount | This is the amount of the transaction in kobo |
charge | This is the charge the customer paid |
reference | This is the unique reference generated by Payfonte for this transaction. |
externalReference | This is the reference sent to us by you when initializing the transaction. |
provider | This is the provider used for this transaction |
channel | This is the channel for this transaction. This can be card, ussd, cryptocurrency and so on |
user | This is a user object containing at least one of email, phone number or name |
{
"event": "payment.completed",
"clientId": "payfonte",
"data": {
"clientId": "Payfonte",
"reference": "Payfonte_development_1682882716958",
"externalReference": "Payfonte_development_1682882716958",
"platformReference": "644ec09c4c2604002fac9d17",
"amount": 100,
"provider": "paystack",
"channel": "card",
"status": "success",
"charge": 0,
"chargeFee": 0,
"paymentCard": {
"deletedAt": null,
"first6Pan": "408408",
"last4Pan": "4081",
"userId": "644ec099ca0ac522ae18555e",
"authorizationCode": "AUTH_407z0h7txb",
"bank": "TEST BANK",
"cardType": "visa ",
"clientId": "Payfonte",
"countryCode": "NG",
"createdAt": "2023-04-30T19:37:10.605Z",
"expiry": {
"month": "12",
"year": "2030"
},
"provider": "paystack",
"updatedAt": "2023-04-30T19:37:10.605Z",
"id": "644ec366821b0b8a5986bc55"
},
"user": {
"name": "Payfonte",
"email": "[email protected]"
},
"paidAt": 1682883430,
"integrationLogId": "644ec35e1dd6180dd34a089e"
}
}
Signature Verification
Given that your webhook URL is accessible to the public, it's crucial to confirm that the events are being sent from Payfonte and not from malicious entities. The header of every webhook sent to you will contain a x-webhook-signature
which is a SHA512 encryption using your client-secret
which can be found in Settings -> API Keys/Webhooks
const crypto = require('crypto');
const secret = process.env.CLIENT_SECRET;
// Using Express
app.post("/my/webhook/url", function(req, res) {
//validate event
const hash = crypto.createHmac('sha512', secret).update(JSON.stringify(req.body)).digest('hex');
if (hash == req.headers['x-webook-signature']) {
// get the request's body
const event = req.body;
// process this event
}
res.send(200);
Webhook Order and Priority
The order of webhook priority is as follow:
- If a webhook url is sent with the request to generate a checkout url, we will use that else
- if a webhook url is set when creating a provider integration, we will use that
- we will use the webhook set in the setting section of the dashboard.