本文目录导读:

在 PHP 中生成 RSA 密钥对,主要有两种方式:OpenSSL 扩展(推荐)和 phpseclib 库。
以下是详细的操作步骤和代码示例:
使用 OpenSSL 扩展(最常用)
这是 PHP 内置的扩展,大多数服务器默认已启用,使用 openssl_pkey_new() 函数生成密钥,然后导出公钥和私钥。
<?php
// 1. 配置密钥生成参数
$config = [
"private_key_bits" => 2048, // 密钥位数(推荐 2048 或 4096)
"private_key_type" => OPENSSL_KEYTYPE_RSA,
// "digest_alg" => "sha256", // 可选:指定摘要算法
];
// 2. 生成密钥对(返回资源类型)
$keyPair = openssl_pkey_new($config);
if (!$keyPair) {
die("密钥生成失败: " . openssl_error_string());
}
// 3. 导出私钥
$privateKey = '';
$success = openssl_pkey_export($keyPair, $privateKey);
if (!$success) {
die("私钥导出失败: " . openssl_error_string());
}
// 4. 导出公钥
$publicKeyDetails = openssl_pkey_get_details($keyPair);
if (!$publicKeyDetails) {
die("公钥导出失败: " . openssl_error_string());
}
$publicKey = $publicKeyDetails['key'];
// 5. 清理密钥资源(释放内存)
openssl_pkey_free($keyPair);
// 6. 打印输出
echo "私钥(PEM 格式):\n" . $privateKey . "\n\n";
echo "公钥(PEM 格式):\n" . $publicKey . "\n";
?>
输出示例(私钥和公钥):
私钥(PEM 格式):
-----BEGIN PRIVATE KEY-----
MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcw...(很长的字符串)
-----END PRIVATE KEY-----
公钥(PEM 格式):
-----BEGIN PUBLIC KEY-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBC...(较短的字符串)
-----END PUBLIC KEY-----
使用 phpseclib 库(纯 PHP,适合不装 OpenSSL 的环境)
如果你的服务器没有 OpenSSL 扩展(比如某些共享主机),可以使用 Composer 安装 phpseclib/phpseclib,它不需要 OpenSSL 扩展就能生成 RSA 密钥。
步骤:
- 安装库:
composer require phpseclib/phpseclib - 编写生成代码:
<?php
require 'vendor/autoload.php';
use phpseclib\Crypt\RSA;
// 创建 RSA 对象
$rsa = new RSA();
$rsa->setHash('sha256');
$rsa->setMGFHash('sha256');
$rsa->setEncryptionMode(RSA::ENCRYPTION_OAEP);
// 生成 2048 位密钥对
$keys = $rsa->createKey(2048);
// 输出公私钥
echo "私钥:\n" . $keys['privatekey'] . "\n\n";
echo "公钥:\n" . $keys['publickey'] . "\n";
?>
处理生成的密钥(保存到文件)
在实际应用中,通常需要将密钥保存到文件或数据库中,以下是保存到文件的示例:
// 假设 $privateKey 和 $publicKey 来自上述代码
file_put_contents('private.pem', $privateKey);
file_put_contents('public.pem', $publicKey);
// 给私钥设置更严格的权限(在 Unix/Linux 上)
chmod('private.pem', 0600);
chmod('public.pem', 0644);
关键要点
- 密钥位数:推荐至少 2048 位(安全系数较高),如果对安全性要求极高可以用 4096 位,但性能会下降。
- 格式:上面生成的是 PEM 格式(Base64 编码,带
-----BEGIN和-----END标记),这是最常见和兼容的格式。 - 实际使用:
- 公钥用于加密和验签(发送给客户端或第三方)。
- 私钥用于解密和签名(必须严格保密,绝不能泄露)。
- 错误处理:如果生成失败,务必使用
openssl_error_string()查看错误信息,通常原因时配置参数不正确或内存不足。
常见问题排查
- openssl_pkey_new() 返回 false:尝试只传递
["private_key_bits" => 2048]不传其他参数,或者检查 PHP 的openssl扩展是否已启用(php -m命令查看)。 - 导出私钥为空:确保
openssl_pkey_export的参数传递正确。 - 性能问题:4096 位密钥生成耗时较长(可能需要几秒钟),如果用于高并发应用,建议预生成并复用密钥对。
选择哪种方式取决于你的环境是否支持 OpenSSL 扩展(推荐),如果不支持再考虑用 phpseclib。