JS实现国密算法SM2加密,后端Java解密

后端的实现过程:

后端首先引入bouncycastle,Maven配置如下:

<dependency>
    <groupId>org.bouncycastle</groupId>
    <artifactId>bcprov-jdk15on</artifactId>
    <version>1.65</version>
</dependency>

后端Java代码如下:

//生成密钥对
X9ECParameters sm2ECParameters = GMNamedCurves.getByName("sm2p256v1");
ECDomainParameters domainParameters = new ECDomainParameters(sm2ECParameters.getCurve(), sm2ECParameters.getG(), sm2ECParameters.getN());
ECKeyPairGenerator keyPairGenerator = new ECKeyPairGenerator();
keyPairGenerator.init(new ECKeyGenerationParameters(domainParameters, SecureRandom.getInstance("SHA1PRNG")));
AsymmetricCipherKeyPair asymmetricCipherKeyPair = keyPairGenerator.generateKeyPair();
 
//私钥,16进制格式,自己保存,格式如a2081b5b81fbea0b6b973a3ab6dbbbc65b1164488bf22d8ae2ff0b8260f64853
BigInteger privatekey = ((ECPrivateKeyParameters) asymmetricCipherKeyPair.getPrivate()).getD();
String privateKeyHex = privatekey.toString(16);
 
//公钥,16进制格式,发给前端,格式如04813d4d97ad31bd9d18d785f337f683233099d5abed09cb397152d50ac28cc0ba43711960e811d90453db5f5a9518d660858a8d0c57e359a8bf83427760ebcbba
ECPoint ecPoint = ((ECPublicKeyParameters) asymmetricCipherKeyPair.getPublic()).getQ();
String publicKeyHex = Hex.toHexString(ecPoint.getEncoded(false));

前端Javascript示例代码,写了个页面:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title>SM2-TEST</title>
    <script src="crypto-js.js"></script>
    <script src="sm2.js"></script>
    <script>
    function encrypt() {
        //公钥,16进制格式,由后端生成
        var pubkeyHex = "04813d4d97ad31bd9d18d785f337f683233099d5abed09cb397152d50ac28cc0ba43711960e811d90453db5f5a9518d660858a8d0c57e359a8bf83427760ebcbba";
        var encryptData = sm2Encrypt("SM2 Encryption Test", pubkeyHex, 0);
        console.log(encryptData);
    }
    </script>
</head>
<body onload="encrypt()">
</body>
</html>
 

执行会生成密文,每次生成都会不同,比如我的环境某次生成如下:

04be17bf6fe47da1f34a01ad0ff67901241b72d103e998f2f7cc78a004703bdfb8d2c6e3939f4f708f3a57d872d58ec5c41bbe5976666bcb01acea43f5a1c68a62cc117c24821d17c3023035641894d7c978a5521f8dc6798515550c73071f9703602e0ee490157729b648c1cc3eb929c1a0501e12a216d42461117402

后端尝试解密:

/JS加密产生的密文
String cipherData = "04be17bf6fe47da1f34a01ad0ff67901241b72d103e998f2f7cc78a004703bdfb8d2c6e3939f4f708f3a57d872d58ec5c41bbe5976666bcb01acea43f5a1c68a62cc117c24821d17c3023035641894d7c978a5521f8dc6798515550c73071f9703602e0ee490157729b648c1cc3eb929c1a0501e12a216d42461117402";
byte[] cipherDataByte = Hex.decode(cipherData);
 
//刚才的私钥Hex,先还原私钥
String privateKey = "a2081b5b81fbea0b6b973a3ab6dbbbc65b1164488bf22d8ae2ff0b8260f64853";
BigInteger privateKeyD = new BigInteger(privateKey, 16);
X9ECParameters sm2ECParameters = GMNamedCurves.getByName("sm2p256v1");
ECDomainParameters domainParameters = new ECDomainParameters(sm2ECParameters.getCurve(), sm2ECParameters.getG(), sm2ECParameters.getN());
ECPrivateKeyParameters privateKeyParameters = new ECPrivateKeyParameters(privateKeyD, domainParameters);
 
//用私钥解密
SM2Engine sm2Engine = new SM2Engine();
sm2Engine.init(false, privateKeyParameters);
 
//processBlock得到Base64格式,记得解码
byte[] arrayOfBytes = Base64.getDecoder().decode(sm2Engine.processBlock(cipherDataByte, 0, cipherDataByte.length));
 
//得到明文:SM2 Encryption Test
String data = new String(arrayOfBytes);


小伙伴们有兴趣想了解内容和更多相关学习资料的请点赞收藏+评论转发+关注我,后面会有很多干货。如果在阅读过程中有疑问,请留言讨论

此份文档详细记录了千道面试题与详解; 
! 
   私信我回复【03】即可免费获取


很多人感叹“学习无用”,实际上之所以产生无用论,
   是因为自己想要的与自己所学的匹配不上,这也就意味着自己学得远远不够。无论是学习还是工作,
    都应该有主动性,所以如果拥有大厂梦,那么就要自己努力去实现它。

以上学习资料均免费放送,最后祝愿各位顺利拿到心仪的offer

作者: 

BoyTNT 

原文出处:JS实现国密算法SM2加密,后端Java解密 - BoyTNT - 博客园

猜你喜欢

转载自blog.csdn.net/weixin_70730532/article/details/124798698