HMAC key check value validation

If you have multiple merchant accounts and have set up notifications with different HMAC keys, it may be difficult to identify the particular HMAC key for notifications. Using this call, you can include the last 6 characters of the HMAC on the GUI to easily match the HMAC key to the notification.

The key check value can be found at the following location:

  1. Sign in to the Customer Area and navigate to Account > Server Communication.
  2. For standard notification, click Edit & Test.
  3. Select Additional Settings.
    HMAC Key (HEX Encoded) should contain the key check value. Example: Already configured (KCV: 670DE0).

Code example

import org.junit.Assert;
import org.junit.Test;
import javax.crypto.Mac;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;
import javax.xml.bind.DatatypeConverter;
import java.io.UnsupportedEncodingException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

public class HmacKeyCheckValueDemo {
    @Test
    public void testHmacKeyCheckValue() {
        // Example HEX Key. Set in customer portal under:
        // Settings -> Server Communication -> Standard Notification
        String keyHex = "35445560190c42f01d8a9869619b60511f12499c75c148f689e1e9945c8a4b95";
        // Key Check Value can be found in customer portal under:
        // Settings -> Server Communication -> Standard Notification -> Edit & Test -> Additional Settings
        // For example: "Already configured (KCV: 670DE0)"
        String keyCheckValue = "670DE0";
        try {
            // decode HEX Key into bytes
            byte[] keyBytes = DatatypeConverter.parseHexBinary(keyHex);
            // get payload in bytes
            byte[] payload = "00000000".getBytes("UTF-8");
            // instantiate the MAC object using HMAC / SHA256
            Mac hmacSha256 = javax.crypto.Mac.getInstance("HmacSHA256");
            // create a key object using the secret key and MAC object
            SecretKey secretKey = new SecretKeySpec(keyBytes, hmacSha256.getAlgorithm());
            // initialise the MAC object
            hmacSha256.init(secretKey);
            // finalise the MAC operation
            byte[] signedPayload = hmacSha256.doFinal(payload);
            // encode the signed payload as a String
            String encodedSignedPayload = DatatypeConverter.printHexBinary(signedPayload);
            // take the last 6 characters of the encodedSignedPayload to obtain the key check value
            String computedKeyCheckValue = encodedSignedPayload.substring(encodedSignedPayload.length() - 6);
            System.out.println("expected KCV: " + keyCheckValue);
            System.out.println("computed KCV: " + computedKeyCheckValue);
            // assert the calculated KCV is equal to the expected KCV
            Assert.assertEquals(keyCheckValue, computedKeyCheckValue);
        } catch (UnsupportedEncodingException e) {
            // UTF-8 should be supported
        } catch (NoSuchAlgorithmException e) {
            // HmacSHA256 should be supported
        } catch (InvalidKeyException e) {
            // The key is invalid
        }
    }
}