JAVA RSA非对称加密、解密
添加了一层 Base64编码 解码,安全性更高,可以省略
1.导入依赖
<!-- 糊涂工具包--> <dependency> <groupId>cn.hutool</groupId> <artifactId>hutool-all</artifactId> <version>5.7.20</version> </dependency>
2.main方法
demo.java
package key; import cn.hutool.core.codec.Base64; import java.util.Map; public class demo { public static void main(String[] args) { // 生成公钥 和 私钥 Map<Integer,String> keyMap = RSATestUtils.genKeyPair(); System.out.println("随机生成的公钥为 : " + keyMap.get(0)); System.out.println("随机生成的私钥为 : " + keyMap.get(1)); // 原数据 String data = "Do you like VAN 游戏 "; System.out.println("加密前内容 : "+data); // 1.使用AES(公钥)加密数据 String dataAES = RSATestUtils.encrypt(data, keyMap.get(0)); System.out.println("加密后的内容为 : " + dataAES); // 2.使用Base64进行编码 String dateBase64 = Base64.encode(dataAES); System.out.println("编码后的内容为 = " + dateBase64); // 3.使用Base64进行解码 String dataAESEnd = Base64.decodeStr(dateBase64); System.out.println("解码后的数据 = " + dataAESEnd); // 4.使用AES(私钥)解密数据 String dataNew = RSATestUtils.decrypt(dataAESEnd,keyMap.get(1)); System.out.println("解密后的数据 : " + dataNew); } }
3.RSA工具类
RSATestUtils.java
package key; import org.apache.tomcat.util.codec.binary.Base64; import javax.crypto.BadPaddingException; import javax.crypto.Cipher; import javax.crypto.IllegalBlockSizeException; import javax.crypto.NoSuchPaddingException; 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; import java.util.HashMap; import java.util.Map; /** * @Author: JCccc * @Description: * @Date: 2020/11/17 9:05 */ public class RSATestUtils { public static void main(String[] args) { //生成公钥和私钥 Map<Integer,String> keyMap = genKeyPair(); //加密字符串 String content = "JCccc-+你/好,我是需要被*加*密*的*内*容。"; System.out.println("加密前内容:"+content); System.out.println("随机生成的公钥为:" + keyMap.get(0)); System.out.println("随机生成的私钥为:" + keyMap.get(1)); String messageEn = encrypt(content, keyMap.get(0)); System.out.println("加密后的内容为:" + messageEn); String messageDe = decrypt(messageEn, keyMap.get(1)); System.out.println("还原后的内容为:" + messageDe); } //随机生成密钥对 public static Map genKeyPair() { // KeyPairGenerator类用于生成公钥和私钥对,基于RSA算法生成对象 KeyPairGenerator keyPairGen = null; try { keyPairGen = KeyPairGenerator.getInstance("RSA"); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } // 初始化密钥对生成器,密钥大小为96-1024位 assert keyPairGen != null; keyPairGen.initialize(1024, new SecureRandom()); // 生成一个密钥对,保存在keyPair中 KeyPair keyPair = keyPairGen.generateKeyPair(); RSAPrivateKey privateKey = (RSAPrivateKey) keyPair.getPrivate(); // 得到私钥 RSAPublicKey publicKey = (RSAPublicKey) keyPair.getPublic(); // 得到公钥 String publicKeyString = new String(Base64.encodeBase64(publicKey.getEncoded())); // 得到私钥字符串 String privateKeyString = new String(Base64.encodeBase64((privateKey.getEncoded()))); // 将公钥和私钥保存到Map Map<Integer, String> keyMap = new HashMap<>(); keyMap.put(0, publicKeyString); //0表示公钥 keyMap.put(1, privateKeyString); //1表示私钥 return keyMap; } /** RSA公钥加密 * @param str 加密字符串 * @param publicKey 公钥 * @return 密文 */ public static String encrypt(String str, String publicKey) { //base64编码的公钥 byte[] decoded = Base64.decodeBase64(publicKey); RSAPublicKey pubKey = null; String outStr = null; try { pubKey = (RSAPublicKey) KeyFactory.getInstance("RSA").generatePublic(new X509EncodedKeySpec(decoded)); Cipher cipher = Cipher.getInstance("RSA"); cipher.init(Cipher.ENCRYPT_MODE, pubKey); outStr = Base64.encodeBase64String(cipher.doFinal(str.getBytes(StandardCharsets.UTF_8))); } catch (InvalidKeySpecException | BadPaddingException | IllegalBlockSizeException | InvalidKeyException | NoSuchPaddingException | NoSuchAlgorithmException e) { e.printStackTrace(); } //RSA加密 return outStr; } /** RSA私钥解密 * @param str 加密字符串 * @param privateKey 私钥 * @return 铭文 */ public static String decrypt(String str, String privateKey) { //64位解码加密后的字符串 byte[] inputByte = Base64.decodeBase64(str.getBytes(StandardCharsets.UTF_8)); //base64编码的私钥 byte[] decoded = Base64.decodeBase64(privateKey); RSAPrivateKey priKey = null; //RSA解密 Cipher cipher = null; String outStr = null; try { priKey = (RSAPrivateKey) KeyFactory.getInstance("RSA").generatePrivate(new PKCS8EncodedKeySpec(decoded)); cipher = Cipher.getInstance("RSA"); cipher.init(Cipher.DECRYPT_MODE, priKey); outStr = new String(cipher.doFinal(inputByte)); } catch (InvalidKeySpecException | NoSuchAlgorithmException | NoSuchPaddingException | BadPaddingException | IllegalBlockSizeException | InvalidKeyException e) { e.printStackTrace(); } return outStr; } }
略、Base64工具类(糊涂工具包自带的更好用)
Base64Utils.java
package key; import sun.misc.BASE64Decoder; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.util.Base64; public class Base64Utils { /** * 加密Base64 * 传入字符串 */ public static String encode(String str) { Base64.Encoder encoder = Base64.getEncoder(); byte[] bytes = encoder.encode(str.getBytes(StandardCharsets.UTF_8)); return new String(bytes, StandardCharsets.UTF_8); } /** * 解密Base64 * 传入字符串 */ public static String decoding(String str) { BASE64Decoder base64decoder = new BASE64Decoder(); try { byte[] encodeByte = base64decoder.decodeBuffer(str); return new String(encodeByte); } catch (IOException e) { return str; } } /** * 将二进制转换成16进制 * * @param buf * @return */ public static String parseByte2HexStr(byte buf[]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf[i] & 0xFF); if (hex.length() == 1) { hex = '0' + hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } /** * 将16进制转换为二进制 * * @param hexStr * @return */ public static byte[] parseHexStr2Byte(String hexStr) { if (hexStr.length() < 1) return null; byte[] result = new byte[hexStr.length() / 2]; for (int i = 0; i < hexStr.length() / 2; i++) { int high = Integer.parseInt(hexStr.substring(i * 2, i * 2 + 1), 16); int low = Integer.parseInt(hexStr.substring(i * 2 + 1, i * 2 + 2), 16); result[i] = (byte) (high * 16 + low); } return result; } }