所以我试图从MySQL DB验证用户的哈希密码,但password_verify
似乎不起作用。我觉得这可能是我做错了。
哈希并存储密码:
// Set POST variables
$firstname = mysqli_real_escape_string($conn, $_POST['firstname']);
$lastname = mysqli_real_escape_string($conn, $_POST['lastname']);
$email = mysqli_real_escape_string($conn, $_POST['email']);
$password = mysqli_real_escape_string($conn, $_POST['password']);
$hashedpwd = password_hash($password, PASSWORD_DEFAULT);
// SQL query & Error Handlers
$sql = "INSERT INTO `users_admin` (Firstname, Lastname, Email, Password) VALUES ('$firstname', '$lastname', '$email', '$hashedpwd')";
检索哈希密码:
if ($row = mysqli_fetch_assoc($result)) {
$user_pass = $row['Password'];
$passwordCheck = password_verify($password, $user_pass);
if (!$passwordCheck) {
header("Location: ../login.php?wrong-password");
exit();
} elseif ($passwordCheck) {
// log in the user
$_SESSION['logged_in'] = true;
$_SESSION['id'] = $row['ID'];
$_SESSION['firstname'] = $row['Firstname'];
$_SESSION['lastname'] = $row['Lastname'];
$_SESSION['email'] = $row['Email'];
header("Location: ../dashboard");
exit();
}
}
password_verify = bool(true)
if (isset($_POST['submit'])) {
include('DB_Connect.php');
$email = mysqli_real_escape_string($conn, $_POST['email']);
$password = mysqli_real_escape_string($conn, $_POST['password']);
// error handlers
$sql = "SELECT * FROM users_admin WHERE Email = '$email'";
$result = mysqli_query($conn, $sql);
$resultCheck = mysqli_num_rows($result);
if ($resultCheck < 1) {
header("Location: ../login.php?input:invalid");
exit();
} else {
if ($row = mysqli_fetch_assoc($result)) {
$user_pass = $row['Password'];
$passwordCheck = password_verify($password, $user_pass);
if (!$passwordCheck) {
header("Location: ../login.php?wrong-password");
exit();
} elseif ($passwordCheck) {
// log in the user
$_SESSION['logged_in'] = true;
$_SESSION['id'] = $row['ID'];
$_SESSION['firstname'] = $row['Firstname'];
$_SESSION['lastname'] = $row['Lastname'];
$_SESSION['email'] = $row['Email'];
header("Location: ../dashboard");
exit();
}
}
}
}else{
header("Location: ../login.php?login=error");
exit();
}
答案 0 :(得分:3)
您发布的代码中没有任何内容可导致所述问题。
以下是一些提示和改进:
在散列密码之前,您正在逃避/保护密码。
这样您就可以改变存储的密码
让
$password = $_POST['password'];
在您创建帐户时以及在登录时检查密码是否匹配时。
确保数据库中的Password
字段(存储散列密码)最多可存储255个字符。
建议将结果存储在数据库列中,该列可以扩展到超过60个字符(255个字符将是一个不错的选择)。
如果字段较窄,则会截断哈希,并且您永远不会匹配。
当您在登录时通过电子邮件获得用户时,确保Email
在数据库级别(在表定义中)是唯一的(只要您的主键ID
)
在用户注册和登录时(在php级别)也可以检查这个。
mysqli_fetch_assoc
返回的键值对中的键区分大小写。确保使用与在数据库中命名字段完全相同的密钥来访问值。
实施例。在您的代码中,我读了$row['Email']
。在表格中,字段名称实际为Email
,或者它是email
(小写)?
调试您的代码!
使用调试器或只是放置一个断点,如
var_export( $the_variable );
exit();
in&#34; key&#34;你的代码点。
使用 prepared statements 而不是转义输入并将其直接注入SQL字符串。
哈希并存储密码:
// Set POST variables
$firstname = mysqli_real_escape_string($conn, $_POST['firstname']);
$lastname = mysqli_real_escape_string($conn, $_POST['lastname']);
$email = mysqli_real_escape_string($conn, $_POST['email']);
$password = $_POST['password'];
$hashedpwd = password_hash($password, PASSWORD_DEFAULT);
// SQL query & Error Handlers
$sql = "INSERT INTO `users_admin` (Firstname, Lastname, Email, Password) VALUES ('$firstname', '$lastname', '$email', '$hashedpwd')";
检索哈希密码:
include('DB_Connect.php');
$email = mysqli_real_escape_string($conn, $_POST['email']);
$password = $_POST['password'];
$sql = "SELECT * FROM users_admin WHERE Email = '$email'";
$result = mysqli_query($conn, $sql);
if( $result === false )
{
header("Location: ../login.php?login=error");
exit();
}
$count = mysqli_num_rows($result);
if( $count === 0 )
{
header("Location: ../login.php?input:invalid");
exit();
}
$row = mysqli_fetch_assoc( $result );
$passwordHash = $row['Password'];
$passwordCheck = password_verify( $password, $passwordHash );
if( ! $passwordCheck )
{
header("Location: ../login.php?wrong-password");
exit();
}
// log in the user
$_SESSION['logged_in'] = true;
$_SESSION['id'] = $row['ID'];
$_SESSION['firstname'] = $row['Firstname'];
$_SESSION['lastname'] = $row['Lastname'];
$_SESSION['email'] = $row['Email'];
header("Location: ../dashboard");
exit();
答案 1 :(得分:0)
Paolo的答案很好并且回答了你的问题,我只想向你解释为什么你的密码不一样。
首先,您使用POSTed密码并将其转义:
$password = mysqli_real_escape_string($conn, $_POST['password']);
然后您散列转义的密码:
$hashedpwd = password_hash($password, PASSWORD_DEFAULT);
但是在这里:
$passwordCheck = password_verify($password, $user_pass);
您password_verify
未转义的密码(我假设您没有发布完整代码)
要解决这个问题,请不要忘记密码,这是一个更好的解决方案,因为Paolo在他的回答中建议使用预备声明。