记Java中AES加密踩的坑 Cannot find any provider supporting AES/CBC/PKCS7Padding

一、异常

1.java.security.NoSuchAlgorithmException: Cannot find any provider supporting AES/CBC/PKCS7Padding

解决办法:

1.引入相对应jdk版本的maven依赖 我这里使用的是jdk1.8

        <!-- https://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk15to18 -->
        <dependency>
            <groupId>org.bouncycastle</groupId>
            <artifactId>bcprov-jdk15to18</artifactId>
            <version>1.76</version>
        </dependency>

2.在使用AES前,加入Security.addProvider(new BouncyCastleProvider());

见代码示例:


import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.crush.weixin.entity.UserDO;
import com.crush.weixin.entity.WXAuth;
import com.crush.weixin.mapper.UserMapper;
import lombok.extern.slf4j.Slf4j;
import org.apache.tomcat.util.codec.binary.Base64;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Component;

import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.security.AlgorithmParameters;
import java.security.Security;
import java.util.Random;

@Slf4j
@Component
public class WxService {
    @Autowired
    private StringRedisTemplate redisTemplate;

    @Value("${weixin.session_key}")
    private String sessionKey;

    @Autowired
    UserMapper userMapper;

    static {
        Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());
    }

//这是使用PKCS5Padding 的解密方式 测试下来与PKCS7Padding的结果毫无差别
//    public String wxDecrypt(WXAuth wxAuth) throws Exception {
//        String session_key = redisTemplate.opsForValue().get(sessionKey + wxAuth.getOpenid());
//        log.info("session_Key-信息:" + session_key);
//        byte[] encData = cn.hutool.core.codec.Base64.decode(wxAuth.getEncryptedData());
//        byte[] iv = cn.hutool.core.codec.Base64.decode(wxAuth.getIv());
//        byte[] key = cn.hutool.core.codec.Base64.decode(session_key);
//        AlgorithmParameterSpec ivSpec = new IvParameterSpec(iv);
//        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
//        SecretKeySpec keySpec = new SecretKeySpec(key, "AES");
//        cipher.init(Cipher.DECRYPT_MODE, keySpec, ivSpec);
//        return new String(cipher.doFinal(encData), "UTF-8");
//    }


//PKCS7Padding的解密方式 
    public String decrypt(WXAuth wxAuth) {
        String session_key = redisTemplate.opsForValue().get(sessionKey + wxAuth.getOpenid());
        //被加密的数据  import org.apache.tomcat.util.codec.binary.Base64;
        byte[] dataByte = Base64.decodeBase64(wxAuth.getEncryptedData());
        //加密秘钥
        byte[] keyByte = Base64.decodeBase64(session_key);
        //偏移量
        byte[] ivByte = Base64.decodeBase64(wxAuth.getIv());
        try {
            Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding","BC");
            SecretKeySpec spec = new SecretKeySpec(keyByte, "AES");
            AlgorithmParameters parameters = AlgorithmParameters.getInstance("AES");
            parameters.init(new IvParameterSpec(ivByte));
            cipher.init(Cipher.DECRYPT_MODE, spec, parameters);// 初始化
            byte[] resultByte = cipher.doFinal(dataByte);
            if (null != resultByte && resultByte.length > 0) {
                String result = new String(resultByte, "UTF-8");
                return result;
            }
            return null;
        } catch (Exception e) {
            log.error("解密失败",e);
            throw new RuntimeException("解密失败");
        }
    }

}

我使用直接下载jar包,改变配置信息都无效,只有如上方法解决了问题

参考资料:

JAVA——DES/ECB/PKCS7Padding加密算法[Cannot find any provider supporting DESEDE/CBC/PKCS7Padding]解决方案-CSDN博客

大家也可以试试下面的方法

记Java中AES加密踩的坑-CSDN博客

  • 10
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值