一、生成密钥
1. 生成私钥
openssl genrsa -out rsa_private_key.pem 1024
2. 生成公钥
openssl rsa -pubout -in rsa_private_key.pem -out rsa_public_key.pem
二、 用PHP实现RSA加密,解密,加签,验签
php内置了很丰富的openssl方法,需要安装php的openssl扩展,方法百度,至于查看,就phpinfo()后查看有没有openssl,操作类如下
<?php declare(strict_types = 1);
/** * RAS加解密类 * * 用于实现RSA加密,解密,加签,验签 * * @author alex.xu <xux851@gmail.com> * @version 1.0.0 * */
class Rsa { /** 私钥 **/ private $_privateKey;
/** 公钥 **/ private $_publicKey;
/** 密钥的存储路径 **/ private $_keyPath;
public function __construct(string $path) { if (empty($path) || !is_dir($path)) throw new \Exception('必须设置密钥的存储路径'); // 设置私钥 $this->_keyPath = $path; $file = $this->_keyPath . DIRECTORY_SEPARATOR . 'rsa_private_key.pem'; $prk = file_get_contents($file); $this->_privateKey = openssl_pkey_get_private($prk); // 设置公钥 $file = $this->_keyPath . DIRECTORY_SEPARATOR . 'rsa_public_key.pem'; $puk = file_get_contents($file); $this->_publicKey = openssl_pkey_get_public($puk); }
/** 设置私钥 */ public function setPrivateKey() { if (is_resource($this->_privateKey)) return true; $file = $this->_keyPath . DIRECTORY_SEPARATOR . 'rsa_private_key.pem'; $prk = file_get_contents($file); $this->_privateKey = openssl_pkey_get_private($prk); return true; }
/** 设置公钥 */ public function setPublicKey() { if (is_resource($this->_publicKey)) return true; $file = $this->_keyPath . DIRECTORY_SEPARATOR . 'rsa_public_key.pem'; $puk = file_get_contents($file); $this->_publicKey = openssl_pkey_get_public($puk); return true; }
/** * 加密 * * @param string $data 要加密的字符串 * @param integer $type 类型 0. 私钥 1. 公钥 * @return string|null * */ public function Encrypt(string $data = '', int $type = 0) { if (empty($data)) return null; $r = $type == 0 ? openssl_private_encrypt($data, $encrypted, $this->_privateKey) : openssl_public_encrypt($data, $encrypted, $this->_publicKey); return $r ? base64_encode($encrypted) : null; }
/** * 解密 * * @param string $data 要解密的字符串 * @param integer $type 类型 0. 私钥 1. 公钥 * @return string|null * */ public function Decrypt(string $encrypted = '', int $type = 0) { if (empty($encrypted)) return null; $encrypted = base64_decode($encrypted); $r = $type == 0 ? openssl_private_decrypt($encrypted, $decrypted, $this->_privateKey) : openssl_public_decrypt($encrypted, $decrypted, $this->_publicKey); return $r ? $decrypted : null; }
/** * 私钥加签 * * @param string $data 要加签的串 * @return string|null * */ public function sign(string $data = '') { if (empty($data)) return null; openssl_sign($data, $sign, $this->_privateKey); $sign = base64_encode($sign); return $sign; }
/** * 公钥验签 * * @param string $data 加密串 * @param string $sign 上一步的验名 * @return bool|null * */ public function verify(string $data = '', string $sign = '') { if (empty($data)) return null; return !!openssl_verify($data, base64_decode($sign), $this->_publicKey); }
/** 释放资源 */ public function __destruct() { $this->_privateKey ?? openssl_free_key($this->_privateKey); $this->_publicKey ?? openssl_free_key($this->_publicKey); } }
|
###三、使用方法
将生成的2个文件放在同目录中
$RSA = new Rsa(dirname(__FILE__));
// 公钥加密 --> 私钥加密
$string = 'del.pub';
$publicString = $RSA->Encrypt($string, 1); echo '公钥加密后:' . $publicString . PHP_EOL;
$privateString = $RSA->Decrypt($publicString); echo '私钥解密后:' . $privateString . PHP_EOL;
// 私钥加签 --> 公钥验签 $sign = $RSA->sign($string); echo '私钥加签后:' . $sign . PHP_EOL; $result = $RSA->verify($string, $sign); echo '验证签名是否正确:' . (string)$result;
|
结果如下:
php Rsa.php 公钥加密后:aFDWf858bi30qnyxQvaVz4vTe4Q4+7OU4p+MkQNA8qtPKGxeh11MvRhdq5udzfQPRi72wyrMkfFnWTs5OTh6fXKA3JJPJyezs0yoEIRDfZDJz0sJKPSrZcU5TpCnnU0F3vjIZjxmQFJmSw3OCzGwlQAecAPdpxmUQgg2kl8yg4M= 私钥解密后:del.pub 私钥加签后:MHXPOJm2J6E/NW9n15q5p+uVZhIeUYZ2t8CauIEGR64bToQ+1m5LKKaN+hpaP0Odc7uG8z8JEVTiAsoWrOuxRF17OiKOYzyCmyU9nD4t8irMvmLmTUdX3Pin1iKXrn8SBj7y466EpENDiBkICcViYNTUf/JgrEs7Gn5YcBm+3HU= 验证签名是否正确:1
|
评论
Twikoo V1.6.31