非对称加密算法之RSA的详细使用
非对称加密
对称加密算法在加密和解密时使用的是同一个秘钥;而非对称加密算法需要两个密钥来进行加密和解密,这两个密钥是公开密钥(public key,简称公钥)和私有密钥(private key,简称私钥)。
如果使用公开密钥对数据进行加密,就只有用对应的私有密钥才能解密。如果使用私有密钥对数据进行加密,只有用对应的公开密钥才能解密。因为加密和解密使用的是两个不同的密钥,所以这种算法叫作非对称加密算法。
私钥一般是有服务器掌握的,公钥则是在客户端使用的。
特点
加密和解密使用不同的密钥
如果使用私钥加密, 只能使用公钥解密
如果使用公钥加密, 只能使用私钥解密
处理数据的速度较慢, 因为安全级别高
常见算法
RSA
ECC
生成公钥和私钥
public static void main(String[] args) throws Exception {
// 加密算法
String algorithm = "RSA";
// 创建密钥对生成器对象
KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance(algorithm);
// 生成密钥对
KeyPair keyPair = keyPairGenerator.generateKeyPair();
// 生成私钥
PrivateKey privateKey = keyPair.getPrivate();
// 生成公钥
PublicKey publicKey = keyPair.getPublic();
// 获取私钥字节数组
byte[] privateKeyEncoded = privateKey.getEncoded();
// 获取公钥字节数组
byte[] publicKeyEncoded = publicKey.getEncoded();
// 对公私钥进行base64编码
String privateKeyString = Base64.encode(privateKeyEncoded);
System.out.println("私钥: " + privateKeyString);
String publicKeyString = Base64.encode(publicKeyEncoded);
System.out.println("公钥: " + publicKeyString);
}
私钥: MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQCDWr19bDz73HUzWTfLux0NAS62ZOOgcHg0HS45PQco2SSFyJAscDFF5Sc3vDvdhQcK50Wx0zwNwarQZz/GjlZBjDsTdcC+RAPu6myRS2YIlqUFxHy2oSli8wPx1GmY5FuVVHNjooZxeRb6T4YzOBKe+tK8pc/y74lhmGIh6TCyL8oRD72YPoI9Vh+OX+/yKrgZ+Tmhs9PIvO993/odwjqveBAN/mPl0WZPrzXMjZpOn7xZV6Vy8QTJxNsm6O3M6i6alpfSUziCltc0o+kOfCyys+zEY93oR/Kioo5rY7m0QxX/HvEoCcXmFwVDEMRUoJE4IY8VsReNXQ58LABLrq93AgMBAAECggEAJEmYGaMiQc4IjrPyBxVdFC+kcPz0KWmIu5ToJSXn6W/7d/4NXklsQ0voBqy4uRy78lYr2dFqQL6k6sfrRXYi/B66X0jjg2yUzZbzgTwcJvk/A5Xhgi6JmW1bRJ6SwYsshdd7vSW0EHsMTwBTKaku876FI1qHVSy5fj2ztnyOWFsXXZwho3YE7rWDyUoaAfFeT4ZeAzn0OwKjRsS/r9bYtCcOn7UoStXoWnZMOu9UVNby+spwlfOu6PcYzTpykG1ZX81R1v1shXf29EEYJW43g3abFlQnOuHttSjpvGFwufe2e0sxKe3QH3u5IirXRAP0gpvfFX3T0DK5kto7GUZxuQKBgQDPCtBuNs57z2vz0knn4FPAM95L/OGa0fRbwAWhFdHhFQ7CxSwhkiGK+lLLIrp8YydkeCi5oALZqBdsTe3lsTvWZQRr/wRmp5DryYurG6DUqLsSfL/gl4OJQYg8Terq7H4csjaNhTSpZXlPa6oHaYL8uoS1zYCE3GepzRAMFyIQwwKBgQCiajVPTTG/hbvezZtWOCrQPQbXnq9ckYCdrRU0f+9v+OV+kJVm0lkQesBcVibkHTlPlVFRXrnlVCDCkHuM+yWPPS63ooIG0xV3o5iuhZgKHo7PmvLTJnkYVD2zKojXN0woVEA7og4bnx4eZGc2bFmCztqvqeHoyarPNGSlo0F7PQKBgQDJv1rtGsDICo3B8DcOGRzjHGfQGeHo0A/R2+JgXne+YZuZlTJ0oAXJfDVzNisMDD6VezUL9GzylQYGBkX73WFWf+b4KW6rbTsdV66elHR65NQtppv+iQWmmNHdGXwBYWNeKRZZfuSa8INuLZZoVJtME6A/27kRPghRgL3TWjNaqwKBgD8c3Ihra+iL1FyZM0LG4sQ24sDJNkXXeM5M4w+ao3W0l6GeF6B0Hw4LVVLMW6KLRKkLUiU3lS9riKtyr8AyG/9UfCH58WMrhY0PMpam7VUJWN+Ny8yHh8kPe0ZzQee34k1NqARETg0nwPF4fK8mXYY6UbqvXk0yiMCqEG5ZSWnVAoGAWl8PH+t29Ec6YDDm3qyh9Qwclbnndg7LALxXupmkNdSRqxVidFSFymtyZ/Aoo5T3k3sMWJ2McPa9f+GfYLQieuHplVSWzT8sVJ707WO9Bp9aqBxnM7+hJe/LepZf7JLPdjBWQ7k1CEg+pcKxspD5BFXCptq7aIvhhqpdtlqZ8W4=
公钥: MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAg1q9fWw8+9x1M1k3y7sdDQEutmTjoHB4NB0uOT0HKNkkhciQLHAxReUnN7w73YUHCudFsdM8DcGq0Gc/xo5WQYw7E3XAvkQD7upskUtmCJalBcR8tqEpYvMD8dRpmORblVRzY6KGcXkW+k+GMzgSnvrSvKXP8u+JYZhiIekwsi/KEQ+9mD6CPVYfjl/v8iq4Gfk5obPTyLzvfd/6HcI6r3gQDf5j5dFmT681zI2aTp+8WVelcvEEycTbJujtzOoumpaX0lM4gpbXNKPpDnwssrPsxGPd6EfyoqKOa2O5tEMV/x7xKAnF5hcFQxDEVKCROCGPFbEXjV0OfCwAS66vdwIDAQAB
保存公钥和私钥到本地文件
public static void main(String[] args) throws Exception {
// 加密算法
String algorithm = "RSA";
//生成密钥对并保存在本地文件中
generateKeyToFile(algorithm, "a.pub", "a.pri");
}
/**
* 生成密钥对并保存在本地文件中
*
* @param algorithm : 算法
* @param pubPath : 公钥保存路径
* @param priPath : 私钥保存路径
*/
private static void generateKeyToFile(String algorithm, String pubPath, String priPath) throws Exception {
// 获取密钥对生成器
KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance(algorithm);
// 获取密钥对
KeyPair keyPair = keyPairGenerator.generateKeyPair();
// 获取公钥
PublicKey publicKey = keyPair.getPublic();
// 获取私钥
PrivateKey privateKey = keyPair.getPrivate();
// 获取byte数组
byte[] publicKeyEncoded = publicKey.getEncoded();
byte[] privateKeyEncoded = privateKey.getEncoded();
// 进行Base64编码
String publicKeyString = Base64.encode(publicKeyEncoded);
String privateKeyString = Base64.encode(privateKeyEncoded);
// 保存文件
FileUtils.writeStringToFile(new File(pubPath), publicKeyString, Charset.forName("UTF-8"));
FileUtils.writeStringToFile(new File(priPath), privateKeyString, Charset.forName("UTF-8"));
}
读取本地私钥与公钥
public static void main(String[] args) throws Exception {
// 加密算法
String algorithm = "RSA";
PrivateKey privateKey = getPrivateKey("a.pri", algorithm);
// 获取私钥字节数组
byte[] privateKeyEncoded = privateKey.getEncoded();
PublicKey publicKey = getPublicKey("a.pub", algorithm);
// 获取公钥字节数组
byte[] publicKeyEncoded = publicKey.getEncoded();
// 对公私钥进行base64编码
String privateKeyString = Base64.encode(privateKeyEncoded);
System.out.println("私钥: " + privateKeyString);
String publicKeyString = Base64.encode(publicKeyEncoded);
System.out.println("公钥: " + publicKeyString);
}
/**
* 读取公钥
*
* @param pulickPath 公钥路径
* @param algorithm 加密算法
*/
public static PublicKey getPublicKey(String pulickPath, String algorithm) throws Exception {
// 将文件内容转为字符串
String publicKeyString = FileUtils.readFileToString(new File(pulickPath), Charset.defaultCharset());
// 获取密钥工厂
KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
// 构建密钥规范 进行Base64解码
X509EncodedKeySpec spec = new X509EncodedKeySpec(Base64.decode(publicKeyString));
// 生成公钥
return keyFactory.generatePublic(spec);
}
/**
* 读取本地私钥
*
* @param priPath 私钥路径
* @param algorithm 加密算法
*/
public static PrivateKey getPrivateKey(String priPath, String algorithm) throws Exception {
// 将文件内容转为字符串
String privateKeyString = FileUtils.readFileToString(new File(priPath), Charset.defaultCharset());
// 获取密钥工厂
KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
// 构建密钥规范 进行Base64解码
PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(Base64.decode(privateKeyString));
// 生成私钥
return keyFactory.generatePrivate(spec);
}
私钥加密与公钥解密
public static void main(String[] args) throws Exception {
String input = "Hello World";
// 加密算法
String algorithm = "RSA";
PrivateKey privateKey = getPrivateKey("a.pri", algorithm);
PublicKey publicKey = getPublicKey("a.pub", algorithm);
// 加密
String encrypt = encryptRSA(algorithm, privateKey, input);
System.out.println("私钥对原文加密: " + encrypt);
//解密
String decrypt = decryptRSA(algorithm, publicKey, encrypt);
System.out.println("公钥对原文解密: " + decrypt);
}
/**
* 读取本地公钥
*
* @param pulickPath 公钥路径
* @param algorithm 加密算法
*/
public static PublicKey getPublicKey(String pulickPath, String algorithm) throws Exception {
// 将文件内容转为字符串
String publicKeyString = FileUtils.readFileToString(new File(pulickPath), Charset.defaultCharset());
// 获取密钥工厂
KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
// 构建密钥规范 进行Base64解码
X509EncodedKeySpec spec = new X509EncodedKeySpec(Base64.decode(publicKeyString));
// 生成公钥
return keyFactory.generatePublic(spec);
}
/**
* 读取本地私钥
*
* @param priPath 私钥路径
* @param algorithm 加密算法
*/
public static PrivateKey getPrivateKey(String priPath, String algorithm) throws Exception {
// 将文件内容转为字符串
String privateKeyString = FileUtils.readFileToString(new File(priPath), Charset.defaultCharset());
// 获取密钥工厂
KeyFactory keyFactory = KeyFactory.getInstance(algorithm);
// 构建密钥规范 进行Base64解码
PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(Base64.decode(privateKeyString));
// 生成私钥
return keyFactory.generatePrivate(spec);
}
/**
* 解密数据
*
* @param algorithm 算法
* @param encrypted 密文
* @param key 密钥
* @return : 原文
*/
public static String decryptRSA(String algorithm, Key key, String encrypted) throws Exception {
// 创建加密对象
Cipher cipher = Cipher.getInstance(algorithm);
// 私钥进行解密
cipher.init(Cipher.DECRYPT_MODE, key);
// 由于密文进行了Base64编码, 在这里需要进行解码
byte[] decode = Base64.decode(encrypted);
// 对密文进行解密
byte[] bytes1 = cipher.doFinal(decode);
return new String(bytes1);
}
/**
* 使用密钥加密数据
*
* @param algorithm 算法
* @param input 原文
* @param key 密钥
* @return 密文
*/
public static String encryptRSA(String algorithm, Key key, String input) throws Exception {
// 创建加密对象
Cipher cipher = Cipher.getInstance(algorithm);
// 初始化加密
cipher.init(Cipher.ENCRYPT_MODE, key);
// 私钥加密
byte[] bytes = cipher.doFinal(input.getBytes());
// 对密文加密后进行Base64编码
return Base64.encode(bytes);
}
私钥对原文加密: P2JaHs+91BbTb2CRhocZWa77EE0Ql5i9+q6rFMR/4JQeGZm3ifYGx9935Hm8An2ypi2NaFCnNzXTtgky1JbH3HvQZuyR7omR/VTsfeaMLVDd+aXWo2B1gSx5ZSyQFjXrd1x7FJS8oa28IGM/Pp6N5SdsO1+VQs/FE/ec20/yRmVKVt9UEdp6COg+e/lGYFx3yyVT/6KTbLavcmxUX+gvRTYiis4xvlkMmpOdL8YVDAmtFwkG9XxyCcZwkp5IhcuasTRJyYo+bIF1y51CtHL9gVCtlunzckz48NDdxCOJY0sdFiDIeU7XpSAQTfV1L5PW1paUhFR8+5jPjxtieLqlwA==
公钥对原文解密: Hello World
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/136961.html