Android RSA加密

和小段討論之後,我覺得現在APP加密還是比較嚴峻的,一個是APP本身被破擊打包,還有一個是接口被利用。

本文主要是想通過加密的方式來防止接口被直接抓包抓到,雖然依舊可破解,但是能讓破解者費點力氣。

生成密鑰

RSA加密的密鑰有兩種,一種是公鑰,另一種是私鑰,公鑰是用來加密的,密鑰用於解密。在實際應用中,將公鑰給Android客戶端,Android客戶端提交數據通過這個公鑰加密後上傳到服務器,服務器用私鑰來解密。上報的時候使用post方法,然後將數據包裝成Json的格式加密。服務器端解析之後也比較方便使用。

  • JAVA的生產key的代碼

    KeyPairGenerator kpg;
        try {
        kpg = KeyPairGenerator.getInstance("RSA");
        // 創建‘密匙對’生成器
        kpg.initialize(512); // 指定密匙長度(取值範圍:512~2048)
        KeyPair kp = kpg.genKeyPair(); // 生成‘密匙對’,其中包含着一個公匙和一個私匙的信息
        PublicKey public_key = kp.getPublic(); // 獲得公匙
        PrivateKey private_key = kp.getPrivate(); // 獲得私匙
    
        BASE64Encoder b64 = new BASE64Encoder();
        String pkStr = b64.encode(public_key.getEncoded());
        String prStr = b64.encode(private_key.getEncoded());
    
        System.out.println("public key is " + pkStr);
        System.out.println("*****************");
        System.out.println("private key is " + prStr);
    } catch (NoSuchAlgorithmException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    

需要說明的是,BASE64Encoder在Android直接自帶Base64類,生產的key轉爲Base64

  • 另一種方式生產RSA的key
    使用openssl的方式生成

生成密鑰 密鑰的長度512-2048

openssl genrsa -out privateKey.pem 1024   

生成公鑰

openssl rsa -in privateKey.pem -out publicKey.pem -pubout

公鑰需要提供私鑰來生成

生成的私鑰沒法直接使用需要使用pkcs8轉碼
所以還需要輸入指令

openssl pkcs8 -topk8 -in privateKey.pem -out pk8_private.pem -nocrypt

指令解釋:-in表示輸入的pem文件,-out表示輸出的文件名,-nocrypt表示無視版權。

加密

加密是通過公鑰來加密的
代碼如下

    try {
        byte[] keyByte = Base64.decode(newPublic, Base64.DEFAULT);
        X509EncodedKeySpec x509ek = new X509EncodedKeySpec(keyByte);
        KeyFactory keyFactory = KeyFactory.getInstance("RSA");
        PublicKey publicKey = keyFactory.generatePublic(x509ek);

        Cipher cipher = Cipher.getInstance("RSA");
        cipher.init(Cipher.ENCRYPT_MODE, publicKey);
        byte[] sbt = source.getBytes();
        byte[] epByte = cipher.doFinal(sbt);
        byte[] epStr = Base64.encode(epByte, Base64.DEFAULT);
        afterDecoder = new String(epStr);
        System.out.println("after decode is " + new String(epStr));
    } catch (NoSuchAlgorithmException | InvalidKeySpecException | NoSuchPaddingException
            | InvalidKeyException | IllegalBlockSizeException | BadPaddingException e) {
        e.printStackTrace();
    }

解密

解密需要用到密鑰
代碼如下

try {
        byte[] keyByte = Base64.decode(newPrivate, Base64.DEFAULT);

        PKCS8EncodedKeySpec s8ek = new PKCS8EncodedKeySpec(keyByte);
        KeyFactory keyFactory = KeyFactory.getInstance("RSA");
        PrivateKey privateKey = keyFactory.generatePrivate(s8ek);

        /** 得到Cipher對象對已用公鑰加密的數據進行RSA解密 */
        Cipher cipher = Cipher.getInstance("RSA");
        cipher.init(Cipher.DECRYPT_MODE, privateKey);
        byte[] b1 = Base64.decode(afterDecoder, Base64.DEFAULT);
        /** 執行解密操作 */
        byte[] b = cipher.doFinal(b1);
        System.out.println("decoder result is " + new String(b));
    } catch (NoSuchAlgorithmException | InvalidKeySpecException | NoSuchPaddingException | InvalidKeyException | IllegalBlockSizeException | BadPaddingException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章