Encrypting Data with CryptoJS' AES

AES encryption and decryption using CryptoJS with key size 256 and random IV

Posted by Adones Pitogo on Nov 4, 2016

Due to the number of attacks throughout the history of internet, people have developed techniques on how to protect themselves against malicious cyber intruders. One of these techniques is the implementation of cryptography in computing. Cryptography has long been existing before computers took over the industry. The earliest known use of cryptography is found in non-standard hieroglyphs carved into monuments from the Old Kingdom of Egypt circa 1900 BCE source.

Today, almost all communication media use encryption - phone calls, emails, text messaging and internet protocols.

What is cryptography?

Cryptography is an art of writting and reading secret messages to prevent unauthorized parties from gaining illegal access to confidential data. The process of writting secret messages is referred to as encryption. While decryption is the process of decoding the secret message, the opposite of encryption. It is used to preserve confidenciality, integrity and non-repudiation and authentication of the message being transmitted from one party to another.

What is AES?

AES stands for Advanced Encryption Standard. In 1997, National Standard of Institute and Technology called the cryptographic community for submissions of new encryption algorithm proposal in place of the old encryption standard (DES). The process of selecting the new standard for encryption algorithm took place during 1997 - 2000 source so this is not ancient history we are talking about fella’s.

AES is now the standard of encryption algorithm in US government agencies including NSA. It is also widely implemented in internet protocols like HTTPS, FTPS, SSL/TLS, routers and communication systems.

Encryption and Decryption using CryptoJS’ AES Implementation

Okay, enough with history. Here’s a demo of encryption and decryption using CryptoJS’s implementation of AES with key size (256), padding (pkcs7), mode (CBC), PBE algorithm (PBKDF2), salt (random), IV (random), iteration count (100).

index.html

<!DOCTYPE html>
<html>

  <head>
    <script src="https://code.jquery.com/jquery-3.1.1.min.js"
  integrity="sha256-hVVnYaiADRTO2PzUGmuLJr8BLUSjGIZsDYGmIJLv2b8="
  crossorigin="anonymous"></script>

  <script src="https://cdnjs.cloudflare.com/ajax/libs/crypto-js/3.1.2/rollups/aes.js"></script>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/crypto-js/3.1.2/rollups/pbkdf2.js"></script>
  </head>

  <body>
    <h1>CryptoJs AES Encryption/Decryption</h1>
    <div id="encrypted"></div>
    <div id="decrypted"></div>
    <script src="script.js"></script>
  </body>

</html>

script.js

var keySize = 256;
var ivSize = 128;
var iterations = 100;

var message = "Hello World";
var password = "Secret Password";


function encrypt (msg, pass) {
  var salt = CryptoJS.lib.WordArray.random(128/8);

  var key = CryptoJS.PBKDF2(pass, salt, {
      keySize: keySize/32,
      iterations: iterations
    });

  var iv = CryptoJS.lib.WordArray.random(128/8);

  var encrypted = CryptoJS.AES.encrypt(msg, key, { 
    iv: iv, 
    padding: CryptoJS.pad.Pkcs7,
    mode: CryptoJS.mode.CBC

  });

  // salt, iv will be hex 32 in length
  // append them to the ciphertext for use  in decryption
  var transitmessage = salt.toString()+ iv.toString() + encrypted.toString();
  return transitmessage;
}

function decrypt (transitmessage, pass) {
  var salt = CryptoJS.enc.Hex.parse(transitmessage.substr(0, 32));
  var iv = CryptoJS.enc.Hex.parse(transitmessage.substr(32, 32))
  var encrypted = transitmessage.substring(64);

  var key = CryptoJS.PBKDF2(pass, salt, {
      keySize: keySize/32,
      iterations: iterations
    });

  var decrypted = CryptoJS.AES.decrypt(encrypted, key, { 
    iv: iv, 
    padding: CryptoJS.pad.Pkcs7,
    mode: CryptoJS.mode.CBC

  })
  return decrypted;
}

var encrypted = encrypt(message, password);
var decrypted = decrypt(encrypted, password);

$('#encrypted').text("Encrypted: "+encrypted);
$('#decrypted').text("Decrypted: "+ decrypted.toString(CryptoJS.enc.Utf8) );

Output:

Encrypted: 0750f33fa0329fcea186e3ef965871562d71226a08e55cd52c6712a33510459ek3sg8pLNMQfXt6OL6uoUeQ==
Decrypted: Hello World

The modes of operation currently available are:

  • CBC (the default)
  • CFB
  • CTR
  • OFB
  • ECB

And the padding schemes currently available are:

  • Pkcs7 (the default)
  • Iso97971
  • AnsiX923
  • Iso10126
  • ZeroPadding
  • NoPadding

The Problem

Although we are transmitting data from client to server using encrypted messages, the data is still being decrypted in the servers before storing them in databases. Your data is only protected when in transit to the destination to prevent MIM or man-in-the-middle attacks. But it’s still stored as plain data or text in the databases. Once those databases are compromised, your data will be readable by the intruder. A common scenario is when nude photos and sex videos of celebrities and high-profile individuals leak to the internet.

To address this problem, I created a simple web application that stores encrypted data in the database. Your data will remain safe even if the server gets compromised. Check out the source on Github.

Sources:

Share: Email Twitter Facebook Google LinkedIn Reddit StumbleUpon Tumblr Buffer Digg