Securing your Payments
This module describes how to secure your payments
How it works
Xpresspay helps secure your payments on the client side using an hash
, we would explain how hash works:
Using an hash
you are meant to sort the payment request parameter's you send in your xpressPayonlineSetup
function, on your server e.g.
[
'publicKey',
'transactionId',
'amount',
'currency',
'country',
'email',
'phoneNumber',
'firstName',
'lastName',
'callbackUrl'
]
We would pick up the parameters you sent in your xpresspayonlineSetup
function sort it, compute the hash and compare the it with the value of hash
to make sure they match. This means that values you hash must match the values you passed to us in your xpresspayonlineSetup
function.
Modus Operandi
- Make sure you send your
hash
value in lower case, the server computes the hash in lowercase so they need to match. - Make sure your values are sorted and hashed using the same letter cases as what you add in your
xpresspayonlineSetup
function i.e. if you hash firstName: JIDENNA, then you need to pass it to the client as firstName: JIDENNA. and vice-versa. - For amount with decimal places, if decimal places have trailing zero's e.g. 100.000 , remove all trailing zero's.
Hash your pay button values on your server and send the hash to the client page
Xpresspay inline secures payment on your site using an hash. You should always create the values you are passing to your inline js script on your server, after creating the value you hash it using a hashing algorithm called Sha 256 . Once the value is hashed send the value to the client and add it as parameter to your inline script. The steps to hash are listed below:
Step 1: Create payment request parameters and values on your server
{
integrityValue: (req, res) => {
const hashedPayload = '';
const body = {
"publicKey": "XPPUBK-fba882fb30efff88ca35a1c86553fd78-X",
"transactionId": ref,
"amount": 100,
"currency": "NGN",
"country": "NG",
"email": "[email protected]",
"phoneNumber": "",
"firstName": "Aminu",
"lastName": "Cincin",
"callbackUrl":"https://www.sample.xpresspayments.com/resp"
} ;
}
{
$pb_key = "XPPUBK-fba882fb30efff88ca35a1c86553fd78-X";
$amount_in_naira = 900;
$email = "[email protected]";
$firstname = "user";
$customer_lastname = "example";
$transactionId = "MV-1838383-JH";
$seckey = "XPSECK-ed1742556a97edb6289d88f4f96279ac-X";
$country = "NG";
$currency = "NGN";
$callback_url = "https://www.sample.xpresspayments.com/resp";
$logo_url = "https://www.sample.xpresspayments.com/resp";
$customer_phone = "+2348185615980";
$options = array(
"publicKey" => $pb_key,
"amount" => $amount_in_naira,
"email" => $customer_email,
"firstName" => $customer_firstname,
"transactionId" => $transactionId,
"lastName" => $customer_lastname,
"country" => $country,
"currency" => $currency,
"phoneNumber" => $customer_phone,
"callbackUrl" =>$callback_url,
"logoURL"=>$logo_url
);
}
Step 2: Sort the parameters this way: Ascii (value) Sort keys of data to send
// The keys in step 1 above are sorted by their ASCII value
const keys = Object.keys(payload).sort();
// The sorted keys would be outputed in this format:
[
'amount',
'callbackUrl',
'country',
'currency',
'email',
'firstName'
'lastName',
'phoneNumber',
'transactionId'
]
// The keys in step 1 above are sorted by their ASCII value
ksort($options);
var_dump($options); // check the order of the keys in the array.
// The sorted keys would be outputed in this format:
array(9) {
["amount"]=>
int(900)
["callbackUrl"]=>
String() "localhost:80/xpresspayments.com"
["country"]=>
string(2) "NG"
["currency"]=>
string(3) "NGN"
["email"]=>
string(16) "[email protected]"
["firstName"]=>
string(4) "user"
["lastName"]=>
string(7) "example"
["phoneNumber"]=>
string(14) "+2348185615980"
["transactionId"]=>
string(13) "MV-1838383-JH"
}
Step 3: Concatenate the values in the order of your sorted keys e.g.
/ The payload is rearranged and the values concatenated in the order of the sorted keys.
for(var index in keys){
const key = keys[index];
hashedPayload += payload[key];
}
// The above sample would output a string that looks like this:
"100https://www.sample.xpresspayments.com/respNGNGNaminu.kabunu@xpresspayments.comAminuCincin877298.9539540611"
// Concatenate your public key with the output string:
" XPPUBK-fba882fb30efff88ca35a1c86553fd78-X100https://www.sample.xpresspayments.com/respNGNGNaminu.kabunu@xpresspayments.comAminuCincin877298.9539540611"
// The payload is rearranged and the values concatenated in the order of the sorted keys.
$hashedPayload = '';
foreach($options as $key => $value){
$hashedPayload .= $value;
}
// The above sample would output a string that looks like this:
100https://www.sample.xpresspayments.com/respNGNGNaminu.kabunu@xpresspayments.comAminuCincin877298.9539540611
// Concatenate your public key with the output string:
XPPUBK-fba882fb30efff88ca35a1c86553fd78-X100https://www.sample.xpresspayments.com/respNGNGNaminu.kabunu@xpresspayments.comAminuCincin877298.9539540611
Step 4: Generate a Sha256 hash of the hashstring and send to your Client page.
// Generate the sha256 hash of the concatenated strings
const sha256Hash = createHash('sha256').update(hashString, 'utf8').digest('hex');
// Send the hash and any dynamic value to your client.
res.json({hash: sha256Hash, transactionId: payload.transactionId});
// Generate the sha256 hash of the concatenated strings
$hash = hash('sha256', $completeHash);
echo "$hash";
Once the user clicks the button for the modal to open up, if they change any value on the browser the modal would not be opened and an error would be returned.
Step 5: Pass the hash to xpresspay.
HTML EMBED
When using the html embed pass it in as
hash
.
<form>
<button type="button" style="cursor:pointer;" value="Pay Now" id="submit">Pay Now</button>
</form>
<script type="text/javascript" src="https://xpresspayonlinepluginssandbox.xpresspayments.com/js/plugin.js"></script> //replace this with when pointing to live <script type="text/javascript" src="https://plugins.xpresspayonline.com/js/plugin.js"></script>
<script>
document.addEventListener("DOMContentLoaded", function(event) {
const paybutton = document.getElementById("submit");
paybutton.addEventListener("click", function(e) {
const API_publicKey = "XPPUBK-fba882fb30efff88ca35a1c86553fd78-X";
var email = document.getElementById("email").value;
const body = {
"publicKey": API_publicKey,
"transactionId": ref,
"amount": 100,
"currency": "NGN",
"country": "NG",
"email": "[email protected]",
"phoneNumber": "",
"firstName": "Abdussamad",
"lastName": "Olaiya",
"hash": "<PASS YOUR HASH HERE>",
"callbackurl":"http://localhost:4300",
meta: [{metaname:"ticketId", metavalue: "ABS1234"}]
}
xpressPayonlineSetup(body);
});
})
</script>
Updated over 4 years ago