How to use RSA between Go and Android

2020-06-26 23:19发布

enter image description here

I (1) create Public key in Go and send it for Android (2) android use below code to Encrypt it's data to send to Go with string type (3) Go get string data and try to Decrypt it, but it can't.

My Go code:

// DecryptWithPrivateKey decrypts data with private key
func DecryptWithPrivateKey(ciphertext []byte, priv *rsa.PrivateKey) []byte {
    plaintext, err := rsa.DecryptPKCS1v15(rand.Reader, priv , ciphertext)
    if err != nil {
        log.Println(err)
    }
    return plaintext
}
.
.
.
so.On("serverpublic", func(msg string) {
mes := []byte(msg)
decbyte :=DecryptWithPrivateKey(data,pr)
str := fmt.Sprintf("%s", decbyte)
log.Println("encript data from Android   ---->"   , str)
})

Android studio code:

public final static String chi="RSA/NONE/PKCS1Padding"; //RSA/ECB/PKCS1Padding

    private static byte[] dec4golang(byte[] src) throws Exception {
        Cipher cipher = Cipher.getInstance(chi);
        cipher.init(Cipher.DECRYPT_MODE, serverrk);
        return cipher.doFinal(src);
    }

    private static byte[] enc4golang(String text, PublicKey pubRSA) throws Exception{
        Cipher cipher = Cipher.getInstance(chi);
        cipher.init(Cipher.ENCRYPT_MODE, pubRSA);
        return cipher.doFinal(text.getBytes("UTF-8")); //i also advice you to use: .getBytes("UTF-8"); instead of data.getBytes();
    }

        public final static String enc4golang(String text){
        try {
            return byte2hex(enc4golang(text, serveruk)); 
//            return enc4golang(text, serveruk).toString();
//            return new String(enc4golang(text, serveruk), "UTF-8");
//            return new String(enc4golang(text, serveruk), Charset.forName("utf-8"));
//            return    Base64.encodeToString(enc4golang(text, serveruk), Base64.DEFAULT);///nodejs
//            return  Base64Utils.encodeToString(enc4golang(text, serveruk));
        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
        return null;
    }

     public static String byte2hex(byte[] b)
    {
        String hs = "";
        String stmp = "";
        for (int n = 0; n < b.length; n ++)
        {
            stmp = Integer.toHexString(b[n] & 0xFF);
            if (stmp.length() == 1)
                hs += ("0" + stmp);
            else
                hs += stmp;
        }
        return hs.toUpperCase();
    }

I think my problem is in these lines:

chi="RSA/NONE/PKCS1Padding"; //RSA/ECB/PKCS1Padding

OR

return byte2hex(enc4golang(text, serveruk));

1条回答
爱情/是我丢掉的垃圾
2楼-- · 2020-06-26 23:40

I have tested it and it worked.

in Go i use this fnction:

func rusdec(encryptedString string , privateKey string) (string, error) {
     base64DecodeBytes, err := base64.StdEncoding.DecodeString(encryptedString)
     if err != nil {
         return "", err
     }
     privateKeyBlock, _ := pem.Decode([]byte(privateKey))
     var pri *rsa.PrivateKey
     pri, parseErr := x509.ParsePKCS1PrivateKey(privateKeyBlock.Bytes)
     if parseErr != nil {
         return "", parseErr
     }
     decryptedData, decryptErr := rsa.DecryptOAEP(sha1.New(), rand.Reader, pri, base64DecodeBytes, nil)
     if decryptErr != nil {
         return "", decryptErr
     }
     return string(decryptedData), nil
}

and in Android studio :

public final static String chi="RSA/ECB/OAEPPadding";

public final static String RSA = "RSA";

private final static int CRYPTO_BITS = 512;

public static PublicKey stringToPublicKeytoserver(String publicKeyString)
    {
        try {
            if (publicKeyString.contains("-----BEGIN PUBLIC KEY-----") || publicKeyString.contains("-----END PUBLIC KEY-----"))
                publicKeyString = publicKeyString.replace("-----BEGIN PUBLIC KEY-----", "").replace("-----END PUBLIC KEY-----", "");
            publicKeyString = publicKeyString.replace("-----BEGIN PUBLIC KEY-----", "");
            publicKeyString = publicKeyString.replace("-----END PUBLIC KEY-----", "");
            byte[] keyBytes = Base64.decode(publicKeyString, Base64.DEFAULT);
            X509EncodedKeySpec spec = new X509EncodedKeySpec(keyBytes);
            KeyFactory keyFactory = KeyFactory.getInstance(RSA);
            serveruk=keyFactory.generatePublic(spec);
            return serveruk;
        } catch (NoSuchAlgorithmException | InvalidKeySpecException e) {
            e.printStackTrace();
            return null;
        }
    }

    
     private static byte[] enc4golang(String text, PublicKey pubRSA) throws Exception{
        Cipher cipher = Cipher.getInstance(chi);
        cipher.init(Cipher.ENCRYPT_MODE, pubRSA);
        return cipher.doFinal(text.getBytes("UTF-8")); //i also advice you to use: .getBytes("UTF-8"); instead of data.getBytes();
    }
    
    
    public final static String enc4golang(String text){
        try {
            return Base64.encodeToString(enc4golang(text, serveruk) ,Base64.DEFAULT);  //send this string to golang
        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
        return null;
    }

public and private Key for Go:

 const priPEM = `-----BEGIN RSA PRIVATE KEY-----
    MIIBOQIBAAJBALEZ+CmY7YN7KWib5Oh0AuWqfHiq3aURV1WGaaBm+X43kF3RRGJd
    HbVdOEb2+YoNyni+LD5CQ4R3T7/f0sePzv0CAwEAAQJAc0MAlSoXotPcjl2vrG4c
    mJbNrcceu9i+a0Ywppl+VVsEPOnapMQsVM04BpJzFmi00S+Sxl0pO1oAX0pwX7Oq
    4QIhAOcncV+SQYlOWoH/phOGkA3y5j0eO2uUfqrXJX0q6/+FAiEAxCMvlkSePzkn
    EROwzJu8tpZrIB6CNZ5KKfhPW7Dj3xkCIEvW1w2iMLpZ6LwKInT5iz3oWb3ns1si
    h0SJ/hTJBlD5AiAKEtyQ1TljeeX9xIsiFyWcIyGhZq+9XUHl4fEBfpZVkQIgMfrj
    qLoCdQH1D5F69WUMYd0n36Xpmqf7L9yV0Ofkz1Y=
    -----END RSA PRIVATE KEY-----`

  const pubPEM = `-----BEGIN PUBLIC KEY-----
MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBALEZ+CmY7YN7KWib5Oh0AuWqfHiq3aUR
V1WGaaBm+X43kF3RRGJdHbVdOEb2+YoNyni+LD5CQ4R3T7/f0sePzv0CAwEAAQ==
-----END PUBLIC KEY-----`
查看更多
登录 后发表回答