RAS加密解密工具类

package org.gocom.coframe.sdk.util;

import org.apache.commons.codec.binary.Base64;
import org.apache.commons.lang3.ArrayUtils;
import org.gocom.coframe.sdk.entity.MqMessage;

import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;

import javax.crypto.Cipher;
import java.security.*;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;

/**
 * @Author w
 * @Date 2021/9/17 16:59
 * @Version 1.0
 */
public class RSAUtil {


    /**
     * RSA最大加密明文大小
     */
    private static final int MAX_ENCRYPT_BLOCK = 117;

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

    public static final String SIGN_ALGORITHMS = "SHA256withRSA";

    public static String ALGORITHM_RSA = "RSA";

    /**
     * 使用公钥将数据加密
     * @param sourceData
     * @param publicKey
     * @return
     */
    public static String publicEncrypt(String sourceData, String publicKey){
        return rsaEncrypt(sourceData,publicKey,false);
    }

    /**
     * 使用私钥将数据加密
     * @param sourceData
     * @param privateKey
     * @return
     */
    public static String privateEncrypt(String sourceData, String privateKey){
        return rsaEncrypt(sourceData,privateKey,true);
    }


    /**
     * 使用公钥解密
     * @param encryptedData
     * @param privateKey
     * @return
     */
    public static String publicDecrypt(String encryptedData, String privateKey) {
        return rsaDecrypt(encryptedData,privateKey,false);
    }

    /**
     * 使用私钥解密
     * @param encryptedData
     * @param privateKey
     * @return
     */
    public static String privateDecrypt(String encryptedData, String privateKey) {
        return rsaDecrypt(encryptedData,privateKey,true);
    }

    protected static String rsaEncrypt(String sourceData, String key,boolean isPrivate){
        try {
            Key key1 = isPrivate ? loadPrivateKey(key) : loadPublicKey(key);
            byte[] data = sourceData.getBytes("utf-8");
            byte[] dataReturn = new byte[0];
            Cipher cipher = Cipher.getInstance(ALGORITHM_RSA);
            cipher.init(Cipher.ENCRYPT_MODE, key1);

            // 加密时超过117字节就报错。为此采用分段加密的办法来加密
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < data.length; i += MAX_ENCRYPT_BLOCK) {
                byte[] doFinal = cipher.doFinal(ArrayUtils.subarray(data, i,i + MAX_ENCRYPT_BLOCK));
                sb.append(new String(doFinal));
                dataReturn = ArrayUtils.addAll(dataReturn, doFinal);
            }

            return Base64.encodeBase64URLSafeString(dataReturn);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    protected static String rsaDecrypt(String encryptedData, String key,boolean isPrivate){
        try {
            Key key1 = isPrivate ? loadPrivateKey(key) : loadPublicKey(key);
            byte[] data = Base64.decodeBase64(encryptedData);

            Cipher cipher = Cipher.getInstance(ALGORITHM_RSA);
            cipher.init(Cipher.DECRYPT_MODE, key1);

            // 解密时超过128字节就报错。为此采用分段解密的办法来解密
            byte[] dataReturn = new byte[0];
            for (int i = 0; i < data.length; i += MAX_DECRYPT_BLOCK) {
                byte[] doFinal = cipher.doFinal(ArrayUtils.subarray(data, i, i + MAX_DECRYPT_BLOCK));
                dataReturn = ArrayUtils.addAll(dataReturn, doFinal);
            }

            return new String(dataReturn);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 私钥加签名
     * @param encryptData
     * @param privateKey
     * @return
     */
    public static String rsaSign(String encryptData, String privateKey) {
        try {
            Signature signature = Signature.getInstance(SIGN_ALGORITHMS);
            signature.initSign(loadPrivateKey(privateKey));
            signature.update(encryptData.getBytes());
            byte[] signed = signature.sign();
            return Base64.encodeBase64URLSafeString(signed);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 公钥验签
     * @param encryptStr
     * @param sign
     * @param publicKey
     * @return
     * @throws Exception
     */
    public static boolean verifySign(String encryptStr, String sign, String publicKey)throws Exception {
        try {
            Signature signature = Signature.getInstance(SIGN_ALGORITHMS);
            signature.initVerify(loadPublicKey(publicKey));
            signature.update(encryptStr.getBytes());
            return signature.verify(Base64.decodeBase64(sign));
        }  catch (NoSuchAlgorithmException e) {
            throw new Exception(String.format("验证数字签名时没有[%s]此类算法", SIGN_ALGORITHMS));
        } catch (InvalidKeyException e) {
            throw new Exception("验证数字签名时公钥无效");
        } catch (SignatureException e) {
            throw new Exception("验证数字签名时出现异常");
        }
    }

    public static PublicKey loadPublicKey(String publicKeyStr) throws Exception {
        byte[] buffer = Base64.decodeBase64(publicKeyStr);
        KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM_RSA);
        X509EncodedKeySpec keySpec = new X509EncodedKeySpec(buffer);
        return keyFactory.generatePublic(keySpec);
    }

    public static PrivateKey loadPrivateKey(String privateKeyStr) throws Exception {
        byte[] buffer = Base64.decodeBase64(privateKeyStr);
        PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(buffer);
        KeyFactory keyFactory = KeyFactory.getInstance(ALGORITHM_RSA);
        return keyFactory.generatePrivate(keySpec);
    }

    public  static String urlsafe_encode (String encryptStr){
        return encryptStr.replaceAll("\\+","-").replaceAll("/","_").replaceAll("=","").replaceAll("(\r\n|\r|\n|\n\r)","");

    }

    public  static String urlsafe_decode(String encryptStr){
        encryptStr= encryptStr.replaceAll("-","+").replaceAll("_","/");
        int mob = encryptStr.length()%4;
        if(mob>0){
            encryptStr+="====".substring(mob);
        }
        return encryptStr;
    }
    
    
    private static final String publicKey = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCv9sg8uEWnXbBm7IxqGH5yYM5bvcFATw77eiM9\n" +
            "p5QWWGbYumm+bean3dllzSwYneGnBuAmmK5rO27agQScOzMMgoHqqvusK+fZpreWTzEbzbQuMeAN\n" +
            "pUmcKfebxZykBjXR7+jSMe/dyd0GtbDcWg4qsijMTIUXVhYoZVThjsWoFwIDAQAB";


    

}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值