v1
latestOpenAPI 3.0.32026-07-26208618579.9 KBPIN operations using PKI
View PIN
This operation retrieves card PIN encrypted with temporary PIN encryption key (tzpk) and tzpk encrypted with the provided RSA public key.
Note: The card-holder device must be generating the RSA key, and must not allow any other system to access the private RSA key. The RSA key should be a temporary one-time use key.
Example flow
Step 1, executed on the CARD-HOLDER DEVICE, generating an RSA key pair
// generate RSA key pair
var kpg = KeyPairGenerator.getInstance("RSA");
kpg.initialize(1024);
var keyPair = kpg.generateKeyPair();
var publicKey = Base64.getEncoder().encodeToString(keyPair.getPublic().getEncoded());
Step 2, executed on the CLIENT BACK-END, requesting the encrypted PIN from the API
// controlId received from pincontrol API
var controlId = "83fa5f55-3dd7-453a-8233-4242a6bad179";
// public RSA key, generated by the card-holder device in Step 1
var publicKey = // fetched from the device
// make request
var pinResponse = pinApiClient.post()
.uri("/pin/v2/view?auditUser={user}", "test")
.bodyValue(Map.of(
"controlId", controlId,
"publicKey", publicKey
))
.retrieve()
.bodyToMono(ViewPinResponse.class)
.block();
Step 3, executed on the CARD-HOLDER DEVICE, decrypting the PIN
// response from the API call done in Step 2, given by the backend
var pinResponse = // given by the backend
// decrypt received tzpk with private key
var rsa = Cipher.getInstance("RSA/ECB/NoPadding");
rsa.init(Cipher.DECRYPT_MODE, keyPair.getPrivate());
var decryptedTzpk = rsa.doFinal(Base64.getDecoder().decode(pinResponse.getTzpk()));
// convert double-length key to triple-length - used if the library support only triple-length 3DES
var tzpk = new byte[24];
System.arraycopy(decryptedTzpk, 0, tzpk, 0, 16);
System.arraycopy(decryptedTzpk, 0, tzpk, 16, 8);
// decrypt pinBlock with tzpk
var des = Cipher.getInstance("DESede/ECB/NoPadding");
des.init(Cipher.DECRYPT_MODE, new SecretKeySpec(tzpk, "DESede"));
var decryptedPinBlock = Hex.toHexString(des.doFinal(Base64.getDecoder().decode(pinResponse.getPinBlock())));
post/v2/view
Query parameters
auditUserstring required
The audit user to log the request
Request body
Example request
{
"controlId": "83fa5f55-3dd7-453a-8233-4242a6bad179",
"publicKey": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDP7yu/kPSEPHjqsUYIfarstoX4mx9PeJPZl/2zYFbN3dOAk0YnJYYC5udW+fkfNoaj2cf20XMrXGAatK/N30P9YoksJg8SINss+zn+/suDL/cRDXnVvYUn8fHwMcNNFYx7RbpYGaZHqshp5D96yfTTESu90nP8wrnjXH8iY4JIewIDAQAB"
}Response
Example response
{
"pinBlock": "tACuB41yyfU=",
"tzpk": "i6IWYm4FzTTBrtGF0FFdcHjEEQh8X3qCUcKkNgIXs2R4jLhECfoUHULWoyUu8T9R90MFZnPOuY5tel1Pww4iyKpRG2ChAwPWaHO2g0j9/xKYDBQHY57HklwBdazp03qU9vJIbmwpEOkrJIW1AW7FpypY4amoO565bCg2WfyG69U="
}