HMAC & AES process to follow:
This process explains the secure request,response and header flow using HMAC(Hash-based Message Authentication Code)and AES(Advanced Encryption Standard)for integration with our API platform.It includes header-level HMAC signing for authentication and AES-based payload encryption for secure data exchange.
Headers Required in Each Request:
| Header | Description |
|---|---|
| requestTimestamp | Epoch timestamp in milliseconds |
| transactionid | Unique transaction ID |
| merchantId | Merchant identifier |
| orderId | Order reference ID |
| clientId | Client authentication key |
| hmacSecret | HMAC signature key |
| Content-Type | Must be application/json |
HMAC Request Signature Generation:
Step1:Credentials
secretkey:e.g.,3FF9CBF87A66A452
Step2:Prepare HMAC String
Example:
POST|/isu/pg/apimerchantOnboarding|application/json|application/json| f8567cd967ed46bfaedd1437f39eb06d|1748337693776| 568364767101810775BC999496C0B33BA7EBEF555A59B96A80DFD8285DA2ABAF
Step3:Generate HMAC Value
ExampleOutput:
a0e73956779d362e039df04af12b45970936074c402bb610401aeafdaeecbc95
Step4:Create Authorization Header
a0e73956779d362e039df04af12b45970936074c402bb610401aeafdaeecbc95
HMAC Validation in Response
Each response includes: Content-Type,Traceid,Timestamp,and Server-Authorization
Step1:Use Same Credentials
secretkey=3FF9CBF87A66A452(sample)
Step2:Construct Response HMAC String
200|application/json|a453c1353|20160528121320| C6ED656BCA63C0BE27128D54DEC93F9A615D6E06CD1BEDA5574FD33FCD25E90A
Step3:Generate HMAC Value
ExampleOutput:
a0e73956779d362e039df04af12b45970936074c402bb610401aeafdaeecbc95
Step4:Validate Server-Authorization Header
client1:27b0428ea48930dd9831b13161ee0323fcc7c91be7b0ac8ac536fadd3638deed
AES Payload Encryption and Decryption
Encryption Overview
Key: Symmetric key(Base64 Encoded)
IV:Randomly generated 16-byte Initialization Vector Output: Base64 encoded(IV+cipher text)
AES Encryption Process
2.Generate 16-byte random IV
3.Encrypt JSON payload using AES/CBC/PKCS5 Padding
4.Concatenate IV + Encrypted bytes Base64 encode the final output
AES Decryption Process
2.Split IV(first 16 bytes) and ciphertext
3.Decrypt using AES key and IV
4.Trim/clean decrypted string to remove noise(till last '}'or']')
Java Implementation(Sample)
//EncryptMethod
{
byte[]decodedKey=Base64.getDecoder().decode(key);
byte[]iv=newbyte[16];
newSecureRandom().nextBytes(iv);
Ciphercipher=Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE,newSecretKeySpec(decodedKey, "AES"),newIvParameterSpec(iv));
byte[]encrypted=cipher.doFinal(incomingJsonReq.toString().getBytes());
byte[]result=newbyte[iv.length+encrypted.length];
System.arraycopy(iv,0,result,0, iv.length);
System.arraycopy(encrypted,0,result,iv.length,encrypted.length);
returnBase64.getEncoder().encodeToString(result);
}
Java Implementation(Sample)
//DecryptMethod
{byte[]
byteCipherText=Base64.getDecoder().decode(encryptedString);
byte[]byteKey=Base64.getDecoder().decode(key);
byte[] iv=Arrays.copyOfRange(byteCipherText,0,16);
byte[]cipherText=Arrays.copyOfRange(byteCipherText,16,byteCipherText.length);
Ciphercipher=Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE,new SecretKeySpec(byteKey,"AES"),new IvParameterSpec(iv));
byte[]bytePlainText=cipher.doFinal(cipherText);
return removeNoise(new String(bytePlainText,StandardCharsets.UTF_8).trim());
}
private String removeNoise(String data)
{
int lastCurlyBrace=data.lastIndexOf('}');
int lastSquareBracket=data.lastIndexOf(']');
int lastIndex=Math.max(lastCurlyBrace, lastSquareBracket);
return lastIndex!=-1?data.substring(0,lastIndex+1):data;
}