Authors: Garima Khandelwal, Abhijit Nawale, & Atul Anand
Introduction
Encryption has become an essential requirement in software development, especially considering the threats associated with processing sensitive data. It is necessary not only for data within our own systems but also for data that we send or receive over the network.
Recently, it has been observed that more projects are requiring AES encryption to secure data in transit. Therefore, we decided to share this knowledge to assist not only the MuleSoft community within Apisero but also those outside in implementing this use case.
Use case
Convert the JSON payload data into an AES-encrypted Base64 string for transmission to the downstream systems. The downstream system will decrypt the payload using the same AES key and IV value, thereby enhancing the overall security of the process.
Glossary
- AES (Advanced Encryption Standard) is a standard used to protect and encrypt sensitive information. This standard is used for encrypting electronic data in transit. It works on a secret key which is used by one system to encrypt and other systems to decrypt.
- An initialization vector (or IV) is an added security layer where the same value encrypted multiple times with the same secret key, will not result in the same encrypted value.
Implementation Details
Initially, MuleSoft’s Crypto module with the JCE Encrypt operation was used, but during implementation, the downstream applications were unable to decrypt the payload using the same AES key.
In the MuleSoft crypto module, there is no option to configure a static IV value; it uses a random IV value.
To solve this problem, logic was written in Java to encrypt the JSON payload using the AES key and IV value.
Below is the Java code to encrypt based on the AES Key and AES IV. Pass the payload, AES Key and AES IV as the value, key and initVector parameter to the encrypt() method.
package com.java.mule;
import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.util.Base64;
public class Encrypt
{
public static String encrypt(String value,final String key,final String initVector)
{
try {
IvParameterSpec iv = new IvParameterSpec(initVector.getBytes("UTF-8"));
SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes("UTF-8"), "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING");
cipher.init(Cipher.ENCRYPT_MODE, skeySpec, iv);
byte[] encrypted = cipher.doFinal(value.getBytes());
return Base64.getEncoder().encodeToString(encrypted);
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
}
Below is the code for decrypting the encrypted string using the AES key and AES IV to validate the encryption.
package com.java.mule;
import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.util.Base64;
public class Decrypt
{
public static String decrypt(String encrypted, String key,String initVector) {
try {
IvParameterSpec iv = new IvParameterSpec(initVector.getBytes("UTF-8"));
SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes("UTF-8"), "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING");
cipher.init(Cipher.DECRYPT_MODE, skeySpec, iv);
byte[] original = cipher.doFinal(Base64.getDecoder().decode(encrypted));
return new String(original);
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
}
Once JAVA code is ready, call the logic from the Mule implementation using the Invoke Static operation of MuleSoft Java module as shown below.

Below is the code logic to decrypt the JSON payload.

Illustration
Below is an example of encrypting a JSON payload using the AES key and initialization vector.
{
"name": "Max Mule",
"email": "max.mule@test.com"
}
Screenshots below shows the payload in transit and its encrypted value.


Below screenshot shows decrypting the same secured value from the previous step using the same AES key and initialization vector. As one can see, the value got decrypted to the same JSON payload used earlier.

