title: How to Encrypt/Decrypt text in a file in Java
body: <p>I have a problem with my code, when I encrypt data, for example, in this case, the simmetric key I encrypted with the receiver's public key, then saved to a text file, when I read that text file and try to decrypt it, using the receiver's private key, I get a different key, therefore I cannot use it to decrypt the encrypted message.</p>
  
  <p>Sender's code:</p>
  
  <pre><code>import java.io.File;
  import java.io.FileInputStream;
  import java.io.FileOutputStream;
  import java.io.InputStream;
  import java.security.KeyStore;
  import java.security.MessageDigest;
  import java.security.PrivateKey;
  import java.security.PublicKey;
  import java.security.cert.CertificateFactory;
  import java.security.cert.X509Certificate;
  import javax.crypto.Cipher;
  import javax.crypto.spec.IvParameterSpec;
  import javax.crypto.spec.SecretKeySpec;
  import org.apache.commons.codec.binary.Base64;
  
  class Sender{
  
  public static void main(String[] args) {
          //infile.txt
          File inFile = new File(args[0]);
          //outfile.txt
          File outFile = new File(args[1]);
          //mykeystore.jks
          File keyStoreFile = new File(args[2]);
          //mykeystore info
          String alias = args[3];
          String password = args[4];
          String storepass = args[5];
          //receptor certificate
          String receptorCert = args[6];
  
          try {
              //Read plain text
              FileInputStream rawDataFromFile = new FileInputStream(inFile);
              byte[] plainText = new byte[(int) inFile.length()];
              rawDataFromFile.read(plainText);
  
              //Create simmetric key
              String key = "Bar12345Bar12345"; // 128 bit key
              String initVector = "RandomInitVector"; // 16 bytes IV
              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);
  
              //Encrypt plaintext
              byte[] ciphertext = cipher.doFinal(plainText);
  
              //Hash plaintext
              MessageDigest md = MessageDigest.getInstance("SHA");
              md.update(plainText);
              byte[] digest = md.digest();
  
              //Encrypt simmetric key with receiver's public key          
              Cipher rsaCipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
              PublicKey receptorPublicKey = getPublicKeyFromCert(receptorCert);
              rsaCipher.init(Cipher.ENCRYPT_MODE, receptorPublicKey);
              byte[] simmetricKey = rsaCipher.doFinal(skeySpec.getEncoded());
  
              //Encrypt hash with my private key
              KeyStore myKeyStore = KeyStore.getInstance("JKS");
              FileInputStream inStream = new FileInputStream(keyStoreFile);
              myKeyStore.load(inStream, storepass.toCharArray());
              PrivateKey privatekey = (PrivateKey) myKeyStore.getKey(alias, password.toCharArray());
              rsaCipher.init(Cipher.ENCRYPT_MODE, privatekey);            
              byte[] encodedHash = rsaCipher.doFinal(digest);
  
              //Write to outputfile
              FileOutputStream outToFile = new FileOutputStream(outFile);
  
              outToFile.write(simmetricKey);
              outToFile.write(encodedHash);
              outToFile.write(ciphertext);
  
              outToFile.close();
              rawDataFromFile.close();
          } catch (Exception e) {
              e.printStackTrace();
              e.getMessage();
          }
      }
      public static PublicKey getPublicKeyFromCert(String certLocation) {
          PublicKey pub = null;
          try {
              InputStream inStream = new FileInputStream(certLocation);
              CertificateFactory cf = CertificateFactory.getInstance("X.509");
              X509Certificate cert = (X509Certificate) cf.generateCertificate(inStream);
              inStream.close();
              pub = (PublicKey) cert.getPublicKey();
  
          } catch (Exception e) {
              e.printStackTrace();
          }
          return pub;
      }
  }
  </code></pre>
  
  <p>Receiver's code:</p>
  
  <pre><code>import java.io.File;
  import java.io.FileInputStream;
  import java.security.KeyStore;
  import java.security.PrivateKey;
  import javax.crypto.Cipher;
  import javax.crypto.spec.IvParameterSpec;
  import javax.crypto.spec.SecretKeySpec;
  import org.apache.commons.codec.binary.Base64;
  
  public class Receiver {
  
      public static void main(String[] args) {
          //Sender's out file
          File inFile = new File(args[0]);
          //receiver's keystore
          File keyStoreFile = new File(args[1]);
          //receiver's keystore info
          String password = args[2];
          String alias = args[3];
          String storepass = args[4];
          //sender's cetificate
          File cert = new File(args[5]);
  
          try {
              //get Sender's out file
              FileInputStream rawDataFromFile = new FileInputStream(inFile);
              byte[] simmetricKey = new byte[256];
              byte[] hash = new byte[256];
              byte[] message;
  
              rawDataFromFile.read(simmetricKey);
              rawDataFromFile.read(hash);
  
              int b = rawDataFromFile.available();
              message = new byte[b];
  
              rawDataFromFile.read(message);
              //decrypt the simmetric key with receiver's private key
              KeyStore myKeyStore = KeyStore.getInstance("JKS");
              FileInputStream inStream = new FileInputStream(keyStoreFile);
              myKeyStore.load(inStream, storepass.toCharArray());
              PrivateKey privatekey = (PrivateKey) myKeyStore.getKey(alias, password.toCharArray());
              //
              Cipher deCipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
              deCipher.init(Cipher.DECRYPT_MODE, privatekey);
  
              byte[] key = deCipher.doFinal(simmetricKey);
  
              System.out.println(Base64.encodeBase64String(key));
  
          } catch (Exception e) {
              System.out.println("Error del sistema " + e);
              e.printStackTrace();
          }
  
      }
  
  }
  </code></pre>
  
  <p><strong>UPDATE:</strong></p>
  
  <p>Now I can decrypt the simmetric key using the receiver's private key. But I dont know how to create a decoder using the same argument when I encrypted the message.</p>
  
  <p>Sender's code to encrypt plain text.</p>
  
  <pre><code>    String key = "Bar12345Bar12345"; // 128 bit key
      String initVector = "RandomInitVector"; // 16 bytes IV
      IvParameterSpec iv = new IvParameterSpec(initVector.getBytes("UTF-8"));
      System.out.println(iv.getIV());
      SecretKeySpec skeySpec = new SecretKeySpec(key.getBytes("UTF-8"), "AES");
      Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5PADDING");
      cipher.init(Cipher.ENCRYPT_MODE, skeySpec, iv);
      byte[] ciphertext = cipher.doFinal(plainText);
  </code></pre>
  
  <p>Receiver's decryption 1</p>
  
  <pre><code>    SecretKeySpec keySpec = new SecretKeySpec(decryptedKeySpec, "AES");
      Cipher decoder = Cipher.getInstance("AES");
      decoder.init(Cipher.DECRYPT_MODE, keyspec);
      byte[] original = descipher.doFinal(message);
  </code></pre>
  
  <blockquote>
    <p>ERROR: Given final block not properly padded</p>
  </blockquote>
  
  <p>Receiver's decryption 2</p>
  
  <pre><code>    SecretKeySpec keySpec = new SecretKeySpec(decryptedKeySpec, "AES");
      Cipher decoder = Cipher.getInstance("AES/CBC/PKCS5PADDING");
      decoder.init(Cipher.DECRYPT_MODE, keyspec);
      byte[] original = descipher.doFinal(message);
  </code></pre>
  
  <blockquote>
    <p>ERROR: Parameters missing</p>
  </blockquote>
  
  <p><strong>FINAL UPDATE:</strong>
  Now my code works, thanks for all the help.
  This code can be downloaded from here (btw, it's in spanish, but i don't think it matters):</p>
  
  <p><a href="https://github.com/OmitsuDemon/cryptography" rel="nofollow">download</a></p>