JCA code sample: encrypting data with AES

The following code fragments show how a text can be encrypted and decrypted with the JCA (Java Cryptography Architecture) API using the AES cryptographic algorithm. Lets assume that we have a text which we want to encrypt, and also a key which we want to use for the encryption (remember that AES is a symmetric encryption algorithm, so the same key is used for both encryption and decryption):

String text = "Sample String which we want to encrypt";
String key = "Bar12345Bar12345";

The first thing we need to do is to get the cipher (the cryptographic algorithm) we want to use, and we also need to create a Key which represents our String-based key we defined above so that it can be used in JCE API calls. Cryptographic algorithms are normally working on binary data, so we also need to get the binary representation of the key first, using an appropriate character set:

Cipher cipher = Cipher.getInstance("AES");
Key aesKey = new SecretKeySpec(key.getBytes(StandardCharsets.ISO_8859_1), "AES");

The Key class has a method getEncoded() which returns the binary representation of the key as a byte[] array. We can use this method do print a hexadecimal dump of the key, and we will get the following output:

0000: 42 61 72 31 32 33 34 35 42 61 72 31 32 33 34 35  Bar12345Bar12345

Note that the key which we created is exactly 16 bytes = 128 bits long. This is the minimum key size supported by AES – and with a default JDK installation, we can not use larger keys. See … for more information how to use larger keys (192 bit and 256 bit). Next, we also need to get the binary representation of the text we want to encrypt, so that it can be fed into the encryption algorithm:

byte[] plaintext = text.getBytes(StandardCharsets.ISO_8859_1);

The dump of the plaintext data looks like this:

0000: 53 61 6D 70 6C 65 20 53 74 72 69 6E 67 20 77 68  Sample String wh
0010: 69 63 68 20 77 65 20 77 61 6E 74 20 74 6F 20 65  ich we want to e
0020: 6E 63 72 79 70 74                                ncrypt

Now, we can use the Ciper.doFinal() method to encrypt the whole plaintext:

cipher.init(Cipher.ENCRYPT_MODE, aesKey);
byte[] ciphertext = cipher.doFinal(plaintext);

The dump of the ciphertext (which is the encrypted data) looks like this:

0000: 29 0F 31 B5 7E D4 BD 02 69 8E C3 8E 87 C9 8A 4A  ).1µ~Ô½.i?Ã??É?J
0010: 2D C6 FB F9 E8 4E C9 F7 34 61 33 9B 46 27 57 49  -ÆûùèNÉ÷4a3?F'WI
0020: 31 44 53 5B 58 C6 1F 8A 99 A0 F5 18 5C EB 6A 05  1DS[XÆ.?? õ.\ëj.

One thing to mention is that the length of the ciphertext has been extended to a multiple of 128 bits – this is the block size which AES is using. Now we can use the ciphertext and decrypt it using the original key:

cipher.init(Cipher.DECRYPT_MODE, aesKey);
byte[] decrypted = cipher.doFinal(ciphertext);

The hexadecimal dump of the decrypted array shows that the data has been properly decrypted:

0000: 53 61 6D 70 6C 65 20 53 74 72 69 6E 67 20 77 68  Sample String wh
0010: 69 63 68 20 77 65 20 77 61 6E 74 20 74 6F 20 65  ich we want to e
0020: 6E 63 72 79 70 74                                ncrypt

The complete runnable sample is available at https://github.com/afester/CodeSamples/blob/master/Java/JCE/src/com/example/AESSample.java.