Skip to content

Instantly share code, notes, and snippets.

@michaelO93
Last active February 11, 2017 23:39
Show Gist options
  • Save michaelO93/590d848a85d353b9c074db013692b423 to your computer and use it in GitHub Desktop.
Save michaelO93/590d848a85d353b9c074db013692b423 to your computer and use it in GitHub Desktop.
Code implementation of charging cards with PIN on Flutterwave using Node.js
//A front-end Javascript that sends the our data to the back-end service.
//... for code brevity
$('#cardpayment').on('submit', function (e) {
e.preventDefault();
var ccnumber = $("input[name='ccnumber']").val().replace(/ /g, ''),
ccmonth = $("input[name='ccmonth']").val(),
ccyear = $("input[name='ccyear']").val(),
cvv = $("input[name='cvv']").val(),
mvalue = $("input[name='mvalue']").val(),
amount = $("input[name='amount']").val(),
desc = $("input[name='desc']").val(),
authmethod = $("select[name='authmodel']").val(),
country = $("select[name='country']").val(),
currency = $("select[name='currency']").val(),
uniqid = Math.round(+new Date() / 1000);
if (ccnumber == "" || ccnumber.length < 15) {
swal("Notice", "Please enter a valid card number", "error");
}
else if (ccmonth == "" || ccyear == "") {
swal("Notice", "Please enter valid card expiry", "error");
}
else if (cvv == "") {
swal("Notice", "Please enter CVV/CVC code", "error");
}
else if (authmethod == "") {
swal("Notice", "Please select an authentication method", "error");
}
else if (authmethod == "PIN" && mvalue.length != 4) {
swal("Notice", "Please enter a valid card PIN", "error");
}
else if (authmethod == "BVN" && mvalue.length != 11) {
swal("Notice", "Please enter a valid card BVN", "error");
}
else if (amount == "") {
swal("Notice", "Please enter an amount", "error");
}
else if (desc == "") {
swal("Notice", "Please enter a description", "error");
}
else {
spin();
$.ajax({
type: 'POST',
url: '/pay/card/',
data: {
cardno: ccnumber,
expirymonth: ccmonth,
expiryyear: ccyear,
cvv: cvv,
authmethod: authmethod,
authvalue: mvalue,
amount: amount,
narration: desc,
custid: uniqid,
currency: currency,
country: country
},
dataType: 'json',
success: function (response) {
if (response.status == 'success') {
unspin();
if (response.data.responsecode == '02' && response.data.responsehtml == null) {
swal({
title: "Enter OTP",
text: response.data.responsemessage,
type: "input",
showCancelButton: false,
closeOnConfirm: false,
animation: "slide-from-top",
inputPlaceholder: "Enter OTP"
}, function (inputValue) {
if (inputValue === false) return false;
if (inputValue === "") {
swal.showInputError("You need to write something!");
return false;
}
spin();
$.ajax({
type: 'POST',
url: '/pay/validate/',
data: {otp: inputValue, oo: response.data.otptransactionidentifier},
dataType: 'json',
success: function (report) {
if (report.data.responseCode == "00") {
unspin();
swal.close();
$('#cardpayment')[0].reset();
swal('Payment Successful', 'Payment with reference code: ' + response.data.transactionreference + ' was successful', 'success');
}
else {
unspin();
swal.close();
swal("Notice", report.data.responsemessage, "error");
}
},
error: function (report) {
unspin();
swal.close();
swal("Notice", "Unable to connect to web service. Please check your internet connection and try again", "error");
}
});
});
}
else if (response.data.responsecode == '02' && response.data.responsehtml != null) {
unspin();
var doc = document.getElementById('modaliframe').contentWindow.document;
doc.open();
doc.write(response.data.responsehtml);
doc.close();
$('#responsemodal').modal('show');
}
else if (response.data.responsecode == '00') {
unspin();
$('#cardpayment')[0].reset();
swal('Payment Successful', 'Payment with reference code: ' + response.data.transactionreference + ' was successful', 'success');
}
else {
unspin();
swal("Notice", response.data.responsemessage, "error");
}
}
else {
unspin();
swal("Notice", response.data.responsemessage, "error");
}
},
error: function (response) {
unspin();
console.log(response);
swal("Notice", "Unable to connect to web service. Please check your internet connection and try again", "error");
}
});
}
});
}
var flutterwave = require("../chargeCardService.js");
//Note: The api key and merchant key are stored in the environmental variable
module.exports = {
cardChargeWithPin: function (req, res, next) {
var data = {
"merchantid": process.env.test_merchant_key,
"amount": flutterwave.encrypt(process.env.test_api_key, req.body.amount),
"cardno": flutterwave.encrypt(process.env.test_api_key, req.body.cardno),
"cvv": flutterwave.encrypt(process.env.test_api_key, req.body.cvv),
"authmodel": flutterwave.encrypt(process.env.test_api_key, req.body.authmethod), //authmodel here is PIN
"currency": flutterwave.encrypt(process.env.test_api_key, req.body.currency),
"country": flutterwave.encrypt(process.env.test_api_key, req.body.country),
"custid": flutterwave.encrypt(process.env.test_api_key, req.body.custid),
"expirymonth": flutterwave.encrypt(process.env.test_api_key, req.body.expirymonth),
"expiryyear": flutterwave.encrypt(process.env.test_api_key, req.body.expiryyear),
"narration": flutterwave.encrypt(process.env.test_api_key, req.body.narration),
"pin": flutterwave.encrypt(process.env.test_api_key, req.body.pin)
};
flutterwave.chargeCardWithPin(data).then(function (response) { //calling our chargeCardService.js
if (response) {
return res.json(response)
}
}).catch(function (error) {
return res.json(error);
})
},
validateCardWithPin: function (req, res) {
var data = {
"merchantid": process.env.test_merchant_key,
"otp": flutterwave.encrypt(process.env.test_api_key, req.body.otp),
"otptransactionidentifier": flutterwave.encrypt(process.env.test_api_key, req.body.oo)
};
flutterwave.validateCardWithPin(data).then(function (response) {
return res.json(response)
}).catch(function (error) {
return res.json(error);
})
};
}
var q = require('q');
var unirest = require('unirest');
var dotenv = require('dotenv');
dotenv.load({path: '.env'});
var baseUrl = process.env.apiUrl; // http://staging1flutterwave.co:8080/pwc/rest/
module.exports = {
chargeCardWithPin: function (data) {
var deferred = q.defer();
console.log(data);
unirest.post(baseUrl + '/card/mvva/pay')
.headers({
'Content-Type': 'application/json'
})
.send(data)
.end(function (response) {
if (response.body.status == 'success') {
deferred.resolve(response.body);
}
deferred.reject(response.body);
});
return deferred.promise;
},
validateCardWithPin: function (data) {
var deferred = q.defer();
console.log(data);
unirest.post(baseUrl + '/card/mvva/pay/validate')
.headers({
'Content-Type': 'application/json'
})
.send(data)
.end(function (response) {
if (response.body.status == 'success') {
deferred.resolve(response.body);
}
deferred.reject(response.body);
});
return deferred.promise;
}
}
var CryptoJS = require('crypto-js');
var forge = require('node-forge');
var utf8 = require("utf8");
module.exports = {
encrypt: function (key, text) {
text = (text) ? text.toString() : '';
key = CryptoJS.MD5(utf8.encode(key)).toString(CryptoJS.enc.Latin1);
key = key + key.substring(0, 8);
var cipher = forge.cipher.createCipher('3DES-ECB', forge.util.createBuffer(key));
cipher.start({iv: ''});
cipher.update(forge.util.createBuffer(text, 'utf-8'));
cipher.finish();
var encrypted = cipher.output;
return ( forge.util.encode64(encrypted.getBytes()) );
}
}
//controls our routing...
var express = require('express');
var router = express.Router(),
flutter = require('../cardChargeController.js');
router.post('/pay/card',function (req,res,next) {
next();
}, flutter.cardChargeWithPin);
router.post('/pay/validate',function (req,res,next) {
next();
}, flutter.validateCardWithPin);
module.exports = router;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment