1

I have a JSON array:

JsonArray people;

Which holds JSON objects representing people.

Currently I am saving them as plaintext in a json file.

try {
    OutputStream out = new FileOutputStream('storage.json');
    JsonWriter writer = Json.createWriter(out);
    writer.writeArray(people);
    writer.close();
} 

However I want these files to be encrypted so that they are worthless without the key to decrypt them.

What is the best way to do this? Should I encrypt the JSON array object or can I just encrypt the entire array before writing it? What is the most recommended Java crypto functions that I should use to do this?

  • 4
    What is your threat model? What are you doing with your JSON array? Are you sending it over the Internet (then, TLS)? Or are you storing it locally? Will you need to leave a secret key in your application, or can you use public key crypto? – lorenzog Dec 8 '15 at 9:42
  • @lorenzog I'm just storing it locally, not sending it anywhere. But the computer its stored on may be used by a few people, so others may have access to files on it. – Curious1 Dec 8 '15 at 15:20
  • 1
    Hi Curious1, before we go into what crypto functions to use, I would like to understand this. If your concern is that the computer is shared (I assume with the same login/access), where/how do you want to keep your keys? Is your plan to encrypt the key itself using a pass-phrase? – wei Dec 8 '15 at 22:15
  • 1) Searilze it with whatever method you like, preferer those with smallest output and built-in compression. 2) Compress if no built-in compression was used. 3) Use whatever your favorite strong encryption library on resulting buffer. – Oleg V. Volkov Dec 30 '15 at 13:10
4

There are many ways to do this.

I would encrypt the JSON at a entire file level rather than encrypting content within it. The alternative is complicated and gives no meaningful security advantage. I recommend using an AEAD cipher (my present recommendation is AES-256 with GCM: aka AES/GCM/NoPadding with 256-bit keys). To use GCM you need to be on Java 8 or later. To use AES-256 with an Oracle JRE you will need the Java Cryptography Extension (JCE) Unlimited Strength Jurisdiction Policy Files installed as documented.

You should make sure to set the authentication tag to include information about location and use (the true filename is a good start) to make it hard to rename or substitute other versions (a form of at-rest replay attack).

However, encrypting the JSON content isn't a complete solution. It just moves the ball a bit. If the attacker still has plaintext access to the private key then it won't be effective.

To protect the private key plaintext you can use a KMS (Key Management Service) on a separate system. That keeps the private key out of memory access on the machine with the encrypted JSON file. You submit the encrypted file content to the KMS to be decrypted on load or vice versa on store.

With those in place you can effectively protect the file from offline attacks (ex: disk image analysis, machine image analysis, backup theft, media theft). Without further defenses, the content of the file is still subject to online attacks of the memory of the machine itself.

0

Best to encrypt the entire file, then write to the file as normal. Same for reading. Here is an example on stackoverflow.

https://stackoverflow.com/questions/5632658/how-to-encrypt-or-decrypt-a-file-in-java

  • 2
    Link-only answers are frowned upon here. Can you include the relevant details from the link in your answer? Also, I'm not sure if the linked answer on SO applies in this case. – schroeder Dec 29 '15 at 20:54

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.