«

PHP密码加密存储

时间:2026-10-22 07:13     作者:emer     分类: 无


PHP密码加密存储

引言

用户密码绝不能明文入库,泄露即灾难。MD5、SHA1是哈希算法但速度快、可被彩虹表破解,不适合存密码。PHP 5.5以后内置password_hash和password_verify,用bcrypt自带盐值和成本因子,是现在注册登录系统的标准做法。

注册:生成哈希入库

$pwd = $_POST['password'];
$hash = password_hash($pwd, PASSWORD_DEFAULT);
// $2y$10$....  直接把这串哈希存数据库
$db->insert('users', ['password' => $hash]);

PASSWORD_DEFAULT默认bcrypt,自动生成随机盐,算法和成本因子都记录在哈希串里,不需要单独存盐字段。

登录:校验密码

$row = $db->find('users', ['username' => $username]);
if ($row && password_verify($inputPwd, $row['password'])) {
    // 密码正确,登录成功
} else {
    // 用户名或密码错误
}

password_verify自动识别哈希里的算法和盐,比对用户输入的明文,返回布尔值。

指定成本因子

$hash = password_hash($pwd, PASSWORD_BCRYPT, ['cost' => 12]);

cost越高计算越慢、抗暴力破解越强,默认10。服务器性能允许可适当调高,太慢会影响登录接口响应。

判断哈希是否需要升级

if (password_needs_rehash($row['password'], PASSWORD_DEFAULT)) {
    $newHash = password_hash($inputPwd, PASSWORD_DEFAULT);
    $db->update('users', ['password' => $newHash], $row['id']);
}

算法或成本升级后,老用户登录时校验通过顺便重算哈希,平滑迁移不用强制改密。

错误做法对比

# 不要这样
md5($pwd);                 # 无盐,彩虹表秒破
sha1($pwd . $salt);        # 自制盐方案,仍可GPU爆破
crypt($pwd);               # 旧接口,参数难控

自己拼盐、用通用哈希函数存密码都是安全隐患,直接用内置密码函数。

注意事项

总结

注册用password_hash生成bcrypt哈希入库,登录用password_verify校验,自带随机盐无需单独存盐。cost成本因子按服务器性能调整,password_needs_rehash在用户登录时平滑升级旧哈希。禁止用MD5、SHA1或自制盐方案存密码,密码字段预留60字符以上,登录失败提示统一,配合HTTPS和密码强度校验构成完整账号安全体系。

标签: PHP Web安全 password_hash bcrypt 密码加密