RSA算法加密/解密和签名/验签工具类

本文涉及的产品
密钥管理服务KMS,1000个密钥,100个凭据,1个月
简介: RSA算法加密/解密和签名/验签工具类

public class RsaUtils {

/**
 * 算法名称
 */
private static final String ALGORITHM = "RSA";
/**
 * 签名算法 MD5withRSA 或 SHA1WithRSA 等
 */
public static final String SIGNATURE_ALGORITHM = "MD5withRSA";
/**
 * 密钥长度默认是1024位:
 * 加密的明文最大长度 = 密钥长度 - 11(单位是字节,即byte)
 */
private static final int KEY_SIZE = 1024;
/**
 * RSA最大加密明文大小
 */
private static final int MAX_ENCRYPT_BLOCK = 117;

/**
 * RSA最大解密密文大小
 */
private static final int MAX_DECRYPT_BLOCK = 128;


/**
 * 获取密钥对
 *
 * @return 密钥对
 */
public static KeyPair getKeyPair() throws Exception {
    KeyPairGenerator generator = KeyPairGenerator.getInstance(ALGORITHM);
    generator.initialize(KEY_SIZE);
    return generator.generateKeyPair();
}

/**
 * 私钥字符串转PrivateKey实例
 *
 * @param privateKey 私钥字符串
 * @return
 */
public static PrivateKey getPrivateKey(String privateKey) throws Exception {
    KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM);
    byte[] decodedKey = Base64.getDecoder().decode(privateKey.getBytes("UTF-8"));// 对私钥进行Base64编码解密
    PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(decodedKey);
    return keyFactory.generatePrivate(keySpec);
}

/**
 * 公钥字符串转PublicKey实例
 *
 * @param publicKey 公钥字符串
 * @return
 */
public static PublicKey getPublicKey(String publicKey) throws Exception {
    KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM);
    byte[] decodedKey = Base64.getDecoder().decode(publicKey.getBytes("UTF-8")); // 对公钥进行Base64编码解密
    X509EncodedKeySpec keySpec = new X509EncodedKeySpec(decodedKey);
    return keyFactory.generatePublic(keySpec);
}

/**
 * 公钥加密
 *
 * @param data      待加密数据
 * @param publicKey 公钥
 * @return
 */
public static String encryptByPublicKey(String data, PublicKey publicKey) {
    try (
            ByteArrayOutputStream out = new ByteArrayOutputStream();
    ) {
        Cipher cipher = Cipher.getInstance(ALGORITHM);
        cipher.init(Cipher.ENCRYPT_MODE, publicKey);
        int inputLen = data.getBytes("UTF-8").length;
        int offset = 0;
        byte[] cache;
        int i = 0;
        // 对数据分段加密
        while (inputLen - offset > 0) {
            if (inputLen - offset > MAX_ENCRYPT_BLOCK) {
                cache = cipher.doFinal(data.getBytes("UTF-8"), offset, MAX_ENCRYPT_BLOCK);
            } else {
                cache = cipher.doFinal(data.getBytes("UTF-8"), offset, inputLen - offset);
            }
            out.write(cache, 0, cache.length);
            i++;
            offset = i * MAX_ENCRYPT_BLOCK;
        }
        byte[] encryptedData = out.toByteArray();
        // 获取加密内容使用Base64进行编码加密,并以UTF-8为标准转化成字符串
        // 加密后的字符串
        //return new String(Base64.encodeBase64String(encryptedData));
        return new String(Base64.getEncoder().encode(encryptedData), "UTF-8");
    } catch (Exception e) {
        e.printStackTrace();
    }
    return null;
}

/**
 * 私钥解密
 *
 * @param data       待解密数据
 * @param privateKey 私钥
 * @return
 */
public static String decryptByPrivateKey(String data, PrivateKey privateKey) {
    try (
            ByteArrayOutputStream out = new ByteArrayOutputStream();
    ) {
        Cipher cipher = Cipher.getInstance(ALGORITHM);
        cipher.init(Cipher.DECRYPT_MODE, privateKey);

        // 对待解密数据进行Base64编码解密
        byte[] dataBytes = Base64.getDecoder().decode(data.getBytes("UTF-8"));
        int inputLen = dataBytes.length;
        int offset = 0;
        byte[] cache;
        int i = 0;
        // 对数据分段解密
        while (inputLen - offset > 0) {
            if (inputLen - offset > MAX_DECRYPT_BLOCK) {
                cache = cipher.doFinal(dataBytes, offset, MAX_DECRYPT_BLOCK);
            } else {
                cache = cipher.doFinal(dataBytes, offset, inputLen - offset);
            }
            out.write(cache, 0, cache.length);
            i++;
            offset = i * MAX_DECRYPT_BLOCK;
        }
        byte[] decryptedData = out.toByteArray();
        // 解密后的内容
        return new String(decryptedData, "UTF-8");
    } catch (Exception e) {
        e.printStackTrace();
    }
    return null;
}

/**
 * 私钥签名
 *
 * @param data       待签名数据
 * @param privateKey 私钥
 * @return 签名
 */
public static String sign(String data, PrivateKey privateKey) throws Exception {
    byte[] keyBytes = privateKey.getEncoded();
    PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM);
    PrivateKey key = keyFactory.generatePrivate(keySpec);
    Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
    signature.initSign(key);
    signature.update(data.getBytes());
    return new String(Base64.getEncoder().encode(signature.sign()));  // 对签名内容进行Base64编码加密
}

/**
 * 公钥验签
 *
 * @param srcData   原始字符串
 * @param publicKey 公钥
 * @param sign      签名
 * @return 是否验签通过
 */
public static boolean verify(byte[] srcData, PublicKey publicKey, String sign) throws Exception {
    byte[] keyBytes = publicKey.getEncoded();
    X509EncodedKeySpec keySpec = new X509EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM);
    PublicKey key = keyFactory.generatePublic(keySpec);
    Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
    signature.initVerify(key);
    signature.update(srcData);
    return signature.verify(Base64.getDecoder().decode(sign));
}

public static void main(String[] args) {
    try {
        // 生成密钥对
        KeyPair keyPair = getKeyPair();
        String privateKey = new String(Base64.getEncoder().encode(keyPair.getPrivate().getEncoded()), "UTF-8");
        String publicKey = new String(Base64.getEncoder().encode(keyPair.getPublic().getEncoded()), "UTF-8");
        System.out.println("私钥:" + privateKey);
        System.out.println("公钥:" + publicKey);
        // RSA加密
        String data = "签名算法可以是NIST标准DSA,使用DSA和SHA-1。 使用SHA-1消息摘要算法的DSA算法可以指定为SHA1withDSA 。 在RSA的情况下,\n" +
                "存在对消息多个选择摘要算法,所以签名算法可被指定为,例如, MD2withRSA , MD5withRSA ,或SHA1withRSA 。 必须指定算法名称,因为没有默认值。";
        String encryptData = encryptByPublicKey(data, getPublicKey(publicKey));
        System.out.println("加密后内容:" + encryptData);
        // RSA解密
        String decryptData = decryptByPrivateKey(encryptData, getPrivateKey(privateKey));
        System.out.println("解密后内容:" + decryptData);

        // RSA签名
        String sign = sign(data, getPrivateKey(privateKey));
        System.out.println("签名内容:" + sign);
        // RSA验签
        boolean result = verify(data.getBytes(), getPublicKey(publicKey), sign);
        System.out.print("验签结果:" + result);

    } catch (Exception e) {
        e.printStackTrace();
        System.out.print("加密解密异常");
    }
}

}

相关文章
|
9天前
|
弹性计算 算法 Linux
使用SM4算法加密LUKS格式磁盘
本文介绍了在Anolis 8操作系统使用cryptsetup对磁盘进行分区、加密和挂载的过程。采用SM4加密算法。具体步骤包括:初始化加密卷、解锁加密分区、格式化并挂载设备。最后,展示了如何取消挂载并关闭加密卷以确保数据安全。整个过程确保了磁盘数据的安全性和隐私保护。
37 2
使用SM4算法加密LUKS格式磁盘
|
5月前
|
安全 算法 网络安全
浅谈非对称加密(RSA)
浅谈非对称加密(RSA)
216 0
|
2月前
|
算法 安全 Go
Go 语言中实现 RSA 加解密、签名验证算法
随着互联网的发展,安全需求日益增长。非对称加密算法RSA成为密码学中的重要代表。本文介绍如何使用Go语言和[forgoer/openssl](https://github.com/forgoer/openssl)库简化RSA加解密操作,包括秘钥生成、加解密及签名验证。该库还支持AES、DES等常用算法,安装简便,代码示例清晰易懂。
64 12
|
4月前
|
算法 安全 Go
RSA加密算法详解与Python和Go实现
RSA加密算法详解与Python和Go实现
327 1
|
4月前
|
算法 安全 网络安全
使用 Python 实现 RSA 加密
使用 Python 实现 RSA 加密
168 2
|
5月前
|
算法 安全 网络安全
概念区分:对称加密、非对称加密、公钥、私钥、签名、证书
概念区分:对称加密、非对称加密、公钥、私钥、签名、证书
233 0
|
1天前
|
算法 数据安全/隐私保护 计算机视觉
基于FPGA的图像双线性插值算法verilog实现,包括tb测试文件和MATLAB辅助验证
本项目展示了256×256图像通过双线性插值放大至512×512的效果,无水印展示。使用Matlab 2022a和Vivado 2019.2开发,提供完整代码及详细中文注释、操作视频。核心程序实现图像缩放,并在Matlab中验证效果。双线性插值算法通过FPGA高效实现图像缩放,确保质量。
|
1月前
|
算法 数据安全/隐私保护 计算机视觉
基于Retinex算法的图像去雾matlab仿真
本项目展示了基于Retinex算法的图像去雾技术。完整程序运行效果无水印,使用Matlab2022a开发。核心代码包含详细中文注释和操作步骤视频。Retinex理论由Edwin Land提出,旨在分离图像的光照和反射分量,增强图像对比度、颜色和细节,尤其在雾天条件下表现优异,有效解决图像去雾问题。
|
1月前
|
算法 数据可视化 安全
基于DWA优化算法的机器人路径规划matlab仿真
本项目基于DWA优化算法实现机器人路径规划的MATLAB仿真,适用于动态环境下的自主导航。使用MATLAB2022A版本运行,展示路径规划和预测结果。核心代码通过散点图和轨迹图可视化路径点及预测路径。DWA算法通过定义速度空间、采样候选动作并评估其优劣(目标方向性、障碍物距离、速度一致性),实时调整机器人运动参数,确保安全避障并接近目标。
146 68
|
1月前
|
算法 数据安全/隐私保护
室内障碍物射线追踪算法matlab模拟仿真
### 简介 本项目展示了室内障碍物射线追踪算法在无线通信中的应用。通过Matlab 2022a实现,包含完整程序运行效果(无水印),支持增加发射点和室内墙壁设置。核心代码配有详细中文注释及操作视频。该算法基于几何光学原理,模拟信号在复杂室内环境中的传播路径与强度,涵盖场景建模、射线发射、传播及接收点场强计算等步骤,为无线网络规划提供重要依据。

热门文章

最新文章