我已将password_hash
PHP函数添加到我的注册页面,用户在其中创建帐户并存储密码。我在注册表单中应用了相同的password_hash
代码行。数据保存在数据库中,但是当我尝试登录时,提交的密码与存储的密码不匹配。我也尝试了password_verify
函数,我在PHP手册中读到过,但没有任何作用。在尝试和尝试之后,我真的不知道还能做什么,所以如果有人有建议,我会很感激。
P.S。我目前正在使用PHP 5.6.25版。
以下是代码:
<?php
// AJAX CALLS THIS LOGIN CODE TO EXECUTE
if(isset($_POST["e"])){
// CONNECT TO THE DATABASE
include_once("PHP_Includes/db.php");
// GATHER THE POSTED DATA INTO LOCAL VARIABLES AND SANITIZE
$e = mysqli_real_escape_string($db, $_POST['e']);
$p = password_hash($_POST['p'], PASSWORD_DEFAULT,['cost' => 15]);
// FORM DATA ERROR HANDLING
if($e == "" || $p == ""){
echo "login_failed";
exit();
} else {
// END FORM DATA ERROR HANDLING
$sql = "SELECT id, username, password FROM users WHERE email='$e' AND activated='1' LIMIT 1";
$query = mysqli_query($db, $sql);
$row = mysqli_fetch_row($query);
$db_id = $row[0];
$db_username = $row[1];
$db_pass_str = $row[2];
if($p != $db_pass_str){
echo "login_failed";
exit();
} else {
// CREATE THEIR SESSIONS
$_SESSION['userid'] = $db_id;
$_SESSION['username'] = $db_username;
$_SESSION['password'] = $db_pass_str;
}
}
exit();
}
?>
login()函数:
function login(){
var e = _("email").value;
var p = _("password").value;
if(e == "" || p == ""){
_("status").innerHTML = "Fill out all of the form data";
} else {
_("loginbtn").style.display = "none";
_("status").innerHTML = 'please wait ...';
var ajax = ajaxObj("POST", "index.php");
ajax.onreadystatechange = function() {
if(ajaxReturn(ajax) == true) {
if(ajax.responseText == "login_failed"){
_("status").innerHTML = "Login unsuccessful, please try again.";
_("loginbtn").style.display = "block";
} else {
window.location = "user.php?u="+ajax.responseText;
}
}
}
ajax.send("e="+e+"&p="+p);
}
}
答案 0 :(得分:3)
您对password_hash()
如何运作的理解有点过时了。与使用sha1()
或md5()
(两者都应避免存储密码!)不同,password_hash()
每次调用都不会返回相同的字符串,即使是相同的字符串。
例如:
var_dump(password_hash("hello_world", PASSWORD_DEFAULT));
var_dump(password_hash("hello_world", PASSWORD_DEFAULT));
输出(例如,password_hash()
返回的字符串每次调用时都会有所不同)
string(60) "$2y$10$Da2HG0dcvfI.3qBivR8Mpu9U5S06PBZ3415lDEh3EcDZ/fELZzHgC"
string(60) "$2y$10$zL6745UkPEvZWS5w1Keco.IKi7ssl.PqldGxucDYHaJW3vgCc366a"
请注意,即使在相同的值上调用了两次函数,它们也是不同的?这意味着您无法将存储的密码与您当前正在进行的$p = password_hash($_POST['p'], PASSWORD_DEFAULT,['cost' => 15]);
进行比较,因为password_hash()
函数每次都返回一个不同的字符串 - 您需要使用函数password_verify()
来验证密码,如下所示
$p = $_POST['p'];
if (password_verify($p, $fromDataBase)) {
// Valid password!
}
所以不是......
$p = password_hash($_POST['p'], PASSWORD_DEFAULT,['cost' => 15]);
你想要
$p = $_POST['p'];
而不是......
if($p != $db_pass_str){
你想要
if (!password_verify($p, $db_pass_str)) {
关于安全的两个注释:
您没有使用准备好的陈述,真的应该这样做!请参阅下面的mysqli_prepare()
链接。您应该将所有用户输入视为危险,因此对所有接受用户输入的SQL查询使用预准备语句。 (当使用准备好的陈述时,你不想使用mysqli_real_escape_string()
- 使用一个或另一个,最好是准备好的陈述!)
您正在会话中存储密码 - 这是非常气馁的,因为会话可以被劫持&#34;。
Readingmaterial: