title: Android Encrypting String using RSA Public key
body: <p>I am working in a project where I have to encrypt password using RSA public key. I tried many samples and solutions from SO like as follows </p>
  
  <ol>
  <li><p><a href="https://stackoverflow.com/questions/37173777/android-rsa-encryption-from-public-string">Android RSA encryption from public string</a></p></li>
  <li><p><a href="https://stackoverflow.com/questions/22228711/rsa-using-spongycastle">RSA using SpongyCastle</a></p></li>
  </ol>
  
  <p>But none of the solutions worked in my case unfortunately. I was getting following exceptions repeatedly if i try with any work around</p>
  
  <p><strong>Error Log:</strong></p>
  
  <pre><code>04-21 07:50:57.876 18842-18842/com.takeoffandroid.passwordencryption W/art: Before Android 4.1, method android.graphics.PorterDuffColorFilter android.support.graphics.drawable.VectorDrawableCompat.updateTintFilter(android.graphics.PorterDuffColorFilter, android.content.res.ColorStateList, android.graphics.PorterDuff$Mode) would have incorrectly overridden the package-private method in android.graphics.drawable.Drawable
  04-21 07:50:57.986 18842-18842/com.takeoffandroid.passwordencryption W/System.err: java.security.spec.InvalidKeySpecException: java.lang.RuntimeException: error:0c0890ba:ASN.1 encoding routines:asn1_check_tlen:WRONG_TAG
  04-21 07:50:57.986 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.org.conscrypt.OpenSSLKey.getPublicKey(OpenSSLKey.java:250)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.org.conscrypt.OpenSSLRSAKeyFactory.engineGeneratePublic(OpenSSLRSAKeyFactory.java:47)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at java.security.KeyFactory.generatePublic(KeyFactory.java:172)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.takeoffandroid.passwordencryption.MainActivity.RSAEncrypt(MainActivity.java:181)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.takeoffandroid.passwordencryption.MainActivity.onCreate(MainActivity.java:80)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.Activity.performCreate(Activity.java:6532)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1108)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2383)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2490)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.ActivityThread.access$900(ActivityThread.java:157)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1351)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.os.Handler.dispatchMessage(Handler.java:102)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.os.Looper.loop(Looper.java:148)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at android.app.ActivityThread.main(ActivityThread.java:5437)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at java.lang.reflect.Method.invoke(Native Method)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err: Caused by: java.lang.RuntimeException: error:0c0890ba:ASN.1 encoding routines:asn1_check_tlen:WRONG_TAG
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.org.conscrypt.NativeCrypto.d2i_PUBKEY(Native Method)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:     at com.android.org.conscrypt.OpenSSLKey.getPublicKey(OpenSSLKey.java:248)
  04-21 07:50:57.987 18842-18842/com.takeoffandroid.passwordencryption W/System.err:  ... 16 more
  </code></pre>
  
  <p><strong>My Requirement:</strong></p>
  
  <p>I have a public key with me and I wanted to encrypt the text entered in the edittext with that public key. For Eg: Password@123 should be encrypted using public key.</p>
  
  <p><strong>Public Key:</strong></p>
  
  <pre><code>public static String PUBLIC_KEY = "-----BEGIN RSA PUBLIC KEY-----\n" +
              "MMDDFDFK43545mmdf499Mdfdasl43ND/GGKLGKL4434safddEcBFfbTZUM517\n" +
              "VDSVFS45fwdGJGGLKGGL332XSA3=d/S/2ETegJPFQ4sjiY7/DsS2o9Gr\n" +
              "asBASF3465243FCDXSDCDxsSFC39NkDiNO2QKNXivAQVpuJeuoDeK\n" +
              "wNGmwDkIsvxBn8u55QpOwvdaRBeLqllJ6xoF6OuwnD0IB4tVDL2MbMVj1U9GtEGL\n" +
              "DJKHSJAH434jjhdds54KkhjbvGJGGGG/Vn4OYNooIWE9uuiyxm2M\n" +
              "AFSDAFXZB546FGHxcvv324FDGJIYTaa346/9xQIDAQAB\n" +
              "-----END RSA PUBLIC KEY-----";
  </code></pre>
  
  <p>Code Implementations I tried:</p>
  
  <p><strong>Sample I:</strong></p>
  
  <pre><code>  public static String encryptDataRSA(final String data) throws IOException {
          final byte[] dataToEncrypt = data.getBytes();
          byte[] encryptedData = null;
  
          try {
  
              PublicKey publicKey = KeyFactory.getInstance("RSA").generatePublic(new X509EncodedKeySpec(RSAUtils.PUBLIC_KEY.getBytes()));
  
              final Cipher cipher = Cipher.getInstance("RSA");
              cipher.init(Cipher.ENCRYPT_MODE, publicKey);
              encryptedData = cipher.doFinal(dataToEncrypt);
  
              try {
                  final String encryptedText = new String(Base64.encode(encryptedData, Base64.DEFAULT), "UTF-8");
                  return encryptedText.toString();
              }
              catch (final UnsupportedEncodingException e1) { return null; }
          } catch (Exception e) { e.printStackTrace(); }
  
          return "ERROR";
      }
  </code></pre>
  
  <p><strong>Sample II:</strong></p>
  
  <pre><code>    public byte[] RSAEncrypt(final String plain) throws NoSuchAlgorithmException, NoSuchPaddingException,
              InvalidKeyException, IllegalBlockSizeException, BadPaddingException, InvalidKeySpecException {
          KeyPairGenerator kpg = KeyPairGenerator.getInstance("RSA");
          kpg.initialize(1024);
          KeyPair kp = kpg.genKeyPair();
          PublicKey publicKey = KeyFactory.getInstance("RSA").generatePublic(new X509EncodedKeySpec(RSAUtils.PUBLIC_KEY.getBytes()));
  
          Cipher cipher = Cipher.getInstance("RSA");
          cipher.init(Cipher.ENCRYPT_MODE, publicKey);
          byte[] encryptedBytes = cipher.doFinal(plain.getBytes());
          System.out.println("EEncrypted?????" + org.apache.commons.codec.binary.Hex.encodeHexString(encryptedBytes));
          return encryptedBytes;
      }
  </code></pre>
  
  <p><strong>Sample III:</strong></p>
  
  <pre><code> public static String encryptRSAToString(String text, String strPublicKey) {
          byte[] cipherText = null;
          String strEncryInfoData="";
          try {
  
              KeyFactory keyFac = KeyFactory.getInstance("RSA");
              KeySpec keySpec = new X509EncodedKeySpec(Base64.decode(strPublicKey.trim().getBytes(), Base64.DEFAULT));
              Key publicKey = keyFac.generatePublic(keySpec);
  
              // get an RSA cipher object and print the provider
              final Cipher cipher = Cipher.getInstance("RSA");
              // encrypt the plain text using the public key
              cipher.init(Cipher.ENCRYPT_MODE, publicKey);
              cipherText = cipher.doFinal(text.getBytes());
              strEncryInfoData = new String(Base64.encode(cipherText,Base64.DEFAULT));
  
          } catch (Exception e) {
              e.printStackTrace();
          }
          return strEncryInfoData.replaceAll("(\\r|\\n)", "");
      }
  </code></pre>
  
  <p>Any help or suggestions would be really helpful to me. Thanks in advance.</p>