DUKPT (Derived Unique Key Per Transaction) with Node JS

DUKPT (Derived Unique Key Per Transaction) with Node JS

DUKPT is a key management scheme which is widely used for encryption and decryption of credit card data in the Payment industry. This scheme ensures the security of encrypted data by generating a unique per every single encryption. It maintains a counter which is incremented per transaction. DUKPT uses this counter to generate a one-time encryption key which will be used to encrypt data. Since this counter is incremented each time encryption happens, a new key is generated per each encryption.

Most common use case of DUKPT is to encrypt credit card information in Point of Sale devices/credit card readers. In this scenario, a new key is generated per each swipe of a credit card, which results in a different encrypted data for the same card per each swipe.

You can find more information about DUKPT in this nice article.

There are many software libraries which implement DUKPT in C#, Java, etc. But I could not find a NodeJS library to perform DUKPT encryption and decryption. Therefore I decided to implement it by myself.

The result was …..

Installing dukpt

You can install dukpt using either npm or yarn.

npm install dukpt --save

or

yarn add dukpt

Encrypting and Decrypting with dukpt

After installing, you need to create a dukpt object by providing BDK (Base Derivation Key) and KSN (Key Serial Number).

const Dukpt = require('dukpt');
const encryptionBDK = '0123456789ABCDEFFEDCBA9876543210;const ksn = 'FFFF9876543210E00008';
const dukpt = new Dukpt(encryptionBDK, ksn);

Once you create dukpt object, you can start encrypting and decrypting data.

To encrypt plain text data:

const plainTextCardData = '<redacted_for_brevity>27189^DOE/JOHN      ^08043210000000725000000?'; // not an actual card data ;)

const options = {
    inputEncoding: 'ascii',     
    outputEncoding: 'hex',    
    encryptionMode: '3DES'
};

const encryptedCardData = dukpt.dukptEncrypt(plainTextCardData, options);

To decrypt encrypted data:

const encryptedCardData = '411D405D7DEDB9D84797F04<redacted_for_brevity>050509277E5F80BE67A2C324900A7E3';
const options = {    
    outputEncoding: 'ascii',   
    decryptionMode: '3DES',    
    trimOutput: true
};
const decryptedCardData = dukpt.dukptDecrypt(encryptedCardData, options);

For more information about usage, please visit the documentation at NPM.

Currently, this module can accept ascii and hex data for encryption and decryption and can generate ascii or hex data as a result of encryption/decryption. At this moment this library only supports TripleDES encryption, but I hope to implement support for AES as well.

Feel free to download and use this library and report any issues at GitHub Repository.

Background Image Source: i.huffpost.com/gen/1410691/images/o-CREDIT-..