工具类实现

package cn.codesensi.util;

import org.springframework.util.Base64Utils;
import javax.crypto.Cipher;
import java.io.ByteArrayOutputStream;
import java.nio.charset.StandardCharsets;
import java.security.*;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.security.spec.InvalidKeySpecException;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;

public class RSAUtil {
    /**
     * 加密算法
     */
    private static final String RSA = "RSA";

    /**
     * 签名算法
     */
    private static final String SIGN_ALGORITHMS = "SHA1WithRSA";


    public static void main(String[] args) throws Exception {
        // 获取密钥
        KeyPair keyPair = getKeyPair();
        String privateKey = Base64Utils.encodeToString(keyPair.getPrivate().getEncoded());
        String publicKey = Base64Utils.encodeToString(keyPair.getPublic().getEncoded());
        System.out.println("私钥=====" + privateKey);
        System.out.println("公钥=====" + publicKey);
    }


    /**
     * 生成秘钥对
     *
     * @return KeyPair 秘钥对
     * @throws NoSuchAlgorithmException 异常
     */
    public static KeyPair getKeyPair() throws NoSuchAlgorithmException {
        KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance(RSA);
        keyPairGenerator.initialize(1024);
        return keyPairGenerator.generateKeyPair();
    }


    /**
     * 将Base64编码后的公钥转换成PublicKey对象
     *
     * @param publicKeyBase64 公钥base64
     * @return PublicKey PublicKey对象
     */
    public static PublicKey getPublicKey(String publicKeyBase64) throws NoSuchAlgorithmException, InvalidKeySpecException {
        byte[] keyBytes = Base64Utils.decodeFromString(publicKeyBase64);
        X509EncodedKeySpec keySpec = new X509EncodedKeySpec(keyBytes);
        KeyFactory keyFactory = KeyFactory.getInstance(RSA);
        return keyFactory.generatePublic(keySpec);
    }

    /**
     * 将Base64编码后的私钥转换成PrivateKey对象
     *
     * @param privateKeyBase64 私钥base64
     * @return PrivateKey  PrivateKey对象
     * @throws NoSuchAlgorithmException InvalidKeySpecException 异常
     */
    public static PrivateKey getPrivateKey(String privateKeyBase64) throws NoSuchAlgorithmException, InvalidKeySpecException {
        byte[] keyBytes = Base64Utils.decodeFromString((privateKeyBase64));
        PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(keyBytes);
        KeyFactory keyFactory = KeyFactory.getInstance(RSA);
        return keyFactory.generatePrivate(keySpec);
    }

    /**
     * 公钥加密
     *
     * @param plaintext       明文
     * @param publicKeyBase64 公钥base64
     * @return 密文数组base64编码后的字符串
     */
    public static String publicKeyEncrypt(String plaintext, String publicKeyBase64) {
        try {
            // 获取明文字节数组
            byte[] bytes = plaintext.getBytes(StandardCharsets.UTF_8);
            Cipher cipher = Cipher.getInstance(RSA);
            // 编码前设定编码方式及密钥
            PublicKey publicKey = getPublicKey(publicKeyBase64);
            cipher.init(Cipher.ENCRYPT_MODE, publicKey);
            int keyBit = getKeySize(publicKey);
            int inputLen = bytes.length;
            ByteArrayOutputStream out = new ByteArrayOutputStream();
            int offSet = 0;
            int step = keyBit / 8 - 11;

            for (int i = 0; inputLen - offSet > 0; offSet = i * step) {
                byte[] cache;
                if (inputLen - offSet > step) {
                    cache = cipher.doFinal(bytes, offSet, step);
                } else {
                    cache = cipher.doFinal(bytes, offSet, inputLen - offSet);
                }
                out.write(cache, 0, cache.length);
                ++i;
            }
            // 密文字节数组
            byte[] ciphertextBytes = out.toByteArray();
            out.close();
            // 返回密文字节数组base64编码后的字符串
            return Base64Utils.encodeToString(ciphertextBytes);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }


    /**
     * 私钥解密
     *
     * @param ciphertext       密文
     * @param privateKeyBase64 私钥base64
     * @return 明文
     */
    public static String privateKeyDecrypt(String ciphertext, String privateKeyBase64) {
        try {
            // 密文base64解码字节数组
            byte[] bytes = Base64Utils.decodeFromString(ciphertext);
            Cipher cipher = Cipher.getInstance(RSA);
            PrivateKey privateKey = getPrivateKey(privateKeyBase64);
            cipher.init(Cipher.DECRYPT_MODE, privateKey);
            int keyBit = getKeySize(privateKey);
            int inputLen = bytes.length;
            ByteArrayOutputStream out = new ByteArrayOutputStream();
            int offSet = 0;
            int step = keyBit / 8;

            for (int i = 0; inputLen - offSet > 0; offSet = i * step) {
                byte[] cache;
                if (inputLen - offSet > step) {
                    cache = cipher.doFinal(bytes, offSet, step);
                } else {
                    cache = cipher.doFinal(bytes, offSet, inputLen - offSet);
                }
                out.write(cache, 0, cache.length);
                ++i;
            }
            // 明文字节数组
            byte[] plaintextBytes = out.toByteArray();
            out.close();
            return new String(plaintextBytes, StandardCharsets.UTF_8);
        } catch (Exception e) {
            return null;
        }
    }

    /**
     * 私钥加签
     *
     * @param ciphertext       密文
     * @param privateKeyBase64 私钥Base64
     * @return 加密后的base64签名
     */
    public static String rsaSign(String ciphertext, String privateKeyBase64) {
        try {
            // 密文字节数组
            byte[] ciphertextBytes = Base64Utils.decodeFromString(ciphertext);
            PrivateKey privateKey = getPrivateKey(privateKeyBase64);
            Signature signature = Signature.getInstance(SIGN_ALGORITHMS);
            signature.initSign(privateKey);
            signature.update(ciphertextBytes);
            byte[] signed = signature.sign();
            return Base64Utils.encodeToString(signed);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 公钥验签
     *
     * @param ciphertext      密文
     * @param sign            签名
     * @param publicKeyBase64 公钥base64
     * @return 是否篡改了数据
     */
    public static boolean rsaSignCheck(String ciphertext, String sign, String publicKeyBase64) {
        try {
            // 密文base64解码字节数组
            byte[] ciphertextBytes = Base64Utils.decodeFromString(ciphertext);
            // 签名base64解码字节数组
            byte[] signBytes = Base64Utils.decodeFromString(sign);
            PublicKey publicKey = getPublicKey(publicKeyBase64);
            Signature signature = Signature.getInstance(SIGN_ALGORITHMS);
            signature.initVerify(publicKey);
            signature.update(ciphertextBytes);
            return signature.verify(signBytes);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }

    /**
     * 获取公钥长度
     *
     * @param publicKey 公钥
     * @return int 公钥长度
     */
    public static int getKeySize(PublicKey publicKey) {
        RSAPublicKey rsaPublicKey = (RSAPublicKey) publicKey;
        return rsaPublicKey.getModulus().bitLength();
    }

    /**
     * 获取私钥长度
     *
     * @param privateKey 私钥
     * @return int 私钥长度
     */
    public static int getKeySize(PrivateKey privateKey) {
        RSAPrivateKey rsaPrivateKey = (RSAPrivateKey) privateKey;
        return rsaPrivateKey.getModulus().bitLength();
    }
}

公钥加密

// 待加密数据字符串
String body = "xxxxx";

// A公钥
final String aPublicKey = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDNkytZEk3AqcA6P5PdspuB7dCnojIYUFMfdHTi/zUexldOEA3let5oq4LqFK7WzM9G0M2PCHx/Zq/oBAO9nZla20VGXtMrBtfgOp7M8sGIG2kq0rY2IpNV3Ck9Nxp3R/HBmwRA41bNiHWPmh+1tH0jcDEcuqTlRZAFXRTfgKeFGQIDAQAB";
// B私钥
final String bPrivateKey = "MIICdwIBADANBgkqhkiG9w0BAQEFAASCAmEwggJdAgEAAoGBALaW9oXgWSe1aPK1MnvmJXSr12A9BCbgG4ic9U+qQVzul41fhyFROb9zF/3IOePeb2J0Lcvv/E18cy+0Jt58u8EJCcP/Cgz7MPYymwEr1irG+cgz7Q/dydfVT5AEgEHyzJWLcZl8ip/BuBu5xeKUQDlelSCKpc7olKK5V+f4/U51AgMBAAECgYEArkxj3p6wXPCW04HXRGEJhlt4CN2WNgofHoU+w6KyLKVyNLlpRIvGRZT35QIbCQRQbbqb8R8RSWKwjmw54o9NpjX5msgdYl7B3bktmNG83inX8LrLAvLE++tjsV6MYDdzrlMEOto5mp3tRohURbUZsJTxuq/TppyGPhifHukomo0CQQDhaEmy9fyhZhwOjdegrvKtR9ZGRecqL3YKKtLnGH3GILugE48buVpAGBbvtVWJ3ziUBK0X4f76fs6xgHn1UwRXAkEAz1782pHNEcSdKmi5mvljmoon9uCdrCbbliMiugDciwiLVncUfvDiBf5lFYKAOhkoLaain22BhK4MX7/L1a5kEwJAedK/YjWIYEKrj0Ih8/oZtoVIzZoiIa6dAUm7yqJ194rhXNa1VaqLmHBslQlQPb+i+Hy+gFXoVMIMO+rP/0Lq6QJBALS+lCFl55nPBzXJpc0ABeLS/FZgHM3J6KcJ5OC+k3vTbK9mh0TFbBvRSgXfgyggeTahASl4ZuVgVoS2RVHv+GUCQFlbO2IKT97HPtz7e1nhRowrfWwStkr5TG9yCrF1QWZ8j+Qq3twEuzfVxXKvmawvyshe38wLoUfARWOP/p/wMTc=";

// 用A公钥加密
String encryptData = RsaSecretUtil.publicKeyEncrypt(body, aPublicKey);
System.out.println("加密后密文=====" + encryptData);
// 用B私钥加签
String signature = RsaSecretUtil.rsaSign(encryptData, bPrivateKey);
System.out.println("签名信息=====" + signature);

私钥解密

// A私钥
final String aPrivateKey = "MIICeAIBADANBgkqhkiG9w0BAQEFAASCAmIwggJeAgEAAoGBAM2TK1kSTcCpwDo/k92ym4Ht0KeiMhhQUx90dOL/NR7GV04QDeV63mirguoUrtbMz0bQzY8IfH9mr+gEA72dmVrbRUZe0ysG1+A6nszywYgbaSrStjYik1XcKT03GndH8cGbBEDjVs2IdY+aH7W0fSNwMRy6pOVFkAVdFN+Ap4UZAgMBAAECgYAyKQG/txaftwu/arnys1z8ZAGwlYPxqM/PcgP/S1Qz0SOGWaZ6YvOXyJml8iwDH3BIEDTH/MMb9vte+nPLNYQwVgPtKJvmLxMxr5UjYjNI7W1PFTicJF3b/G5JrC5U8hxCYOle8CSSJbeneAQFOeUVPFbdHRnS7QkcXcaWhKmHAQJBAPLlrc1GKN17aEvgz6m8C2RGzUr9xxfyij0kz33byD3S1xrqvWSaCPuHPKlWlQonUas/9pdZ8gUbWO2+E/aEtzkCQQDYqhVFJ6ijvnajsdroko51PMWk7QBjPOjZVW65hFY/G3dcYzi1crCAq9XqX8zsco2xN6EenoAyguYuZChrelzhAkEA6gzjEn/edLyrXSI9OALYv0FyJCaxp6OwDQbhYRdctiXp3CgBY2UB7sz7aPjjGCuXCHrT9DdZfA5D/KJBvjNYEQJBAMBzi4Mq8APKeY17vMva6kk+2vxdPHvprZbm6PxGjWlu1z4sMEIUBq20dMXDpL3eHvfsRuRwu8SiOx23/6NARGECQQCDf5E2OsVJW2whBVM76sQDlTkecF5nokXssq/fVbQEQvDDnBt9/OQ9uVp+38eOPXKP25GIr0HH/2IHHuoQQBFa";
// B公钥
final String bPublicKey = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQC2lvaF4FkntWjytTJ75iV0q9dgPQQm4BuInPVPqkFc7peNX4chUTm/cxf9yDnj3m9idC3L7/xNfHMvtCbefLvBCQnD/woM+zD2MpsBK9YqxvnIM+0P3cnX1U+QBIBB8syVi3GZfIqfwbgbucXilEA5XpUgiqXO6JSiuVfn+P1OdQIDAQAB";

// 用A私钥解密
String decryptData = RsaSecretUtil.privateKeyDecrypt(encryptData, aPrivateKey);
System.out.println("解密后明文=====" + decryptData);
// 用B公钥验签
boolean pass = RsaSecretUtil.rsaSignCheck(encryptData, signature, bPublicKey);
System.out.println("是否一致=====" + pass);