[英]What;s wrong with code which is getting user by email and checking for the password?
我是php的新手,并且正在实现一个登录系统,在该系统中,用户输入电子邮件和密码,并检查其在数据库中的存在(phpmyadmin中的mysql)
用户首次注册时,使用此功能对密码进行加密:
/**
* Encrypting password
*
* @param
* password
* returns salt and encrypted password
*/
public function hashSSHA($password) {
$salt = sha1 ( rand () );
$salt = substr ( $salt, 0, 10 );
$encrypted = base64_encode ( sha1 ( $password . $salt, true ) . $salt );
$hash = array (
"salt" => $salt,
"encrypted" => $encrypted
);
return $hash;
}
salt参数是解密密码的密钥,它与用户信息一起存储在数据库中,解密代码为:
/**
* Decrypting password
*
* @param
* salt, password
* returns hash string
*/
public function checkhashSSHA($salt, $password) {
$hash = base64_encode ( sha1 ( $password . $salt, true ) . $salt );
return $hash;
}
当我进入并使用输入的电子邮件和密码来获取用户时,密码将被解密。
/**
* Get user by email and password
*/
public function getUserByEmailAndPassword($email, $password) {
$stmt = $this->conn->prepare ( "SELECT * FROM users WHERE email = ?" );
$stmt->bind_param ( "s", $email );
if ($stmt->execute ()) {
$user = $stmt->get_result ()->fetch_assoc ();
$stmt->close ();
$salt = $user ["salt"];
$hash = $this->checkhashSSHA ( $salt, $user ["encrypted_password"] );
if ($hash == $password) {
return $user;
} else {
return NULL;
}
} else {
return NULL;
}
}
问题是当用户输入正确的电子邮件和密码时,此代码仍返回NULL,我怀疑处理密码部分有问题。
Siguza的答案是正确的,但是您对他的答案的评论反映出一个非常合理的困惑,因为checkhashSSHA()
函数的名称有点误导(即,其名称与其行为不匹配)。 以“ check”开头的函数名称应返回布尔值。 我建议将其更改为:
/**
* Decrypting password
*
* @param
* password, hash, salt
* returns boolean
*/
public function checkhashSSHA($password, $hash, $salt) {
$hash2 = base64_encode ( sha1 ( $password . $salt, true ) . $salt );
return ($hash == $hash2) ;
}
现在更改这两行:
$hash = $this->checkhashSSHA ( $salt, $user ["encrypted_password"] );
if ($hash == $password) {
到这一行:
if (checkhashSSHA($password, $user["encrypted_password"], $salt)) {
现在,它更清晰,更易于使用,并且其行为与其名称匹配。 但是,如果您想增强代码中的命名,请参考以下建议:
checkhashSSHA()
更改为compareHashSSHA()
。 encrypted_password
在数据库中hashed_password
。 更重要的是,sha1哈希算法有点陈旧,也不是很安全。 我建议将其更改为更安全的哈希,例如sha512。 检查此内容,并阅读Kai Petzke的评论全文。
问题在于这两行:
$hash = $this->checkhashSSHA ( $salt, $user ["encrypted_password"] );
if ($hash == $password) {
首先,您要哈希已哈希的密码,而不是纯文本密码。
然后,您将“哈希的哈希”与纯文本密码进行比较。
所以您正在做hash(hash(pw)) == pw
,当它应该是hash(pw) == hash(pw)
。
您只需要交换$user ["encrypted_password"]
和$password
:
$hash = $this->checkhashSSHA ( $salt, $password );
if ($hash == $user ["encrypted_password"]) {
我建议您不要使用sshhash函数,而是查看php函数password_verify()
在此处查看有关该功能和相关功能的文档: http : //php.net/manual/zh/function.password-verify.php
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.