我已经搜索过并发现了一千个关于我的问题的问题,我试图解决但没有得到帮助。所以我为我的具体案例打开了这个帖子,我希望你能帮助我。
我说到了,我正在PDO中创建一个登录系统,是初学者,但我希望它能在一段时间内通过cookie登录。
我做了几次测试,但没有结果。浏览器已关闭,必须重新输入凭据。
我再说一遍,我已经在网站上搜索过,但还没有设法解决。
的login.php
if (empty($_POST) === false) {
$username = trim($_POST['username']);
$password = trim($_POST['password']);
if (empty($username) === true || empty($password) === true) {
$errors[] = 'Sorry, but we need your username and password.';
} else if ($users->user_exists($username) === false) {
$errors[] = 'Sorry that username doesn\'t exists.';
} else if ($users->email_confirmed($username) === false) {
$errors[] = 'Sorry, but you need to activate your account. Please check your email.';
} else {
$login = $users->login($username, $password);
if ($login === false) {
$errors[] = 'Sorry, that username/password is invalid';
} else {
$_SESSION['id'] = $login; // The user's id is now set into the user's session in the form of $_SESSION['id']
$_SESSION['username'] = $usr;
$cookie_name = '_name_cookie_';
$hash = password_hash($password, PASSWORD_BCRYPT, ["cost" => 12]); // will result in a 32 characters hash
$cookie_time = (3600 * 24 * 30); // 30 days
setcookie($cookie_name, 'usr='.$usr.'&hash='.$hash, time() + $cookie_time);
header('Location: home.php');
exit();
}
}
}
课程: users.php
public function login($username, $password) {
$this->db->query("SELECT * FROM users WHERE username = :username");
$this->db->bind(':username', $username);
$data = $this->db->single();
$hash = $data['password'];
$id = $data['id'];
#hashing the supplied password and comparing it with the stored hashed password.
if (password_verify($password, $hash)) {
return $id;
}else{
return false;
}
}
注意:目前在形式上我不想整合检查"记住我",我稍后会这样做。
但是,我不能如何保持登录用户,cookie被正确插入,否则它不起作用。我该如何解决?
答案 0 :(得分:1)
有几种方法可以做到这一点,有些方法比其他方法更好。有关于它的一些信息,甚至在这个网站上,但我会支出这个概念。
首先,您需要某种令牌或其他东西来识别客户端的用户。这通常使用$_COOKIE
来完成。我喜欢设置两个单独的cookie,一个具有用户ID,另一个具有散列令牌,因此即使有人猜到令牌(这是极不可能的),他们也需要匹配的用户ID。使用代码中的示例,这将是生成所述cookie的示例代码
// Define variables
define("COOKIE_DURATION", time()+60*60*24*30); // 30 days
$userHash = hash("sha256", $_SESSION['id'].time());
// Set the cookies
setcookie("RememberMeID", $_SESSION['id'], COOKIE_DURATION);
setcookie("RememberMeHash", $userHash, COOKIE_DURATION);
这使用当前时间和用户名组合,然后散列,以便我们可以将其用作标识符。我已经使用了sha256
,因为它不是我们存储的密码,应该没问题。
接下来,我们需要识别具有这两个cookie的用户。因此,这些数据也必须存储在服务器中,因此我们可以在用户访问网站时匹配它们。您可以使用数据库,例如包含此信息的单独rememberMe
表。这可能包含您之前使用用户ID创建的哈希。因此,您需要将其插入数据库中。
$stmt = $pdo->prepare("INSERT INTO rememberMe (userID, userHash) VALUES (:id, :hash)");
$stmt->execute(array("id" => $_SESSION['id'], "hash" => $userHash));
然后,您可以简单地检查两个cookie是否都已设置,而会话未设置,查看数据是否匹配 - 如果匹配,则设置其会话!
// If we're not logged in, and the two cookies are set, we can check if something matches
if (!isset($_SESSION['id']) && !empty($_COOKIE['RememberMeID']) && !empty($_COOKIE['RememberMeHash'])) {
// Check if the cookies match something in the DB...
$stmt = $pdo->prepare("SELECT COUNT(*) as `count`, userID FROM rememberMe WHERE userID=:id AND userHash=:hash");
$stmt->execute(array("id" => $_COOKIE['RememberMeID'], "hash" => $_COOKIE['RememberMeHash']));
$row = $stmt->fetch(PDO::FETCH_ASSOC);
// If it does, we log them in and renew the cookie
if ($row['count'] > 0) {
$_SESSION['id'] = $row['userID'];
setcookie("RememberMeID", $_SESSION['id'], COOKIE_DURATION);
setcookie("RememberMeHash", $_COOKIE['RememberMeHash'], COOKIE_DURATION);
}
}
您还可以阅读以下主题:What is the best way to implement "remember me" for a website?
答案 1 :(得分:0)
非常感谢你的帮助。我当时正在这样做:
if (empty($_POST) === false) {
$username = trim($_POST['username']);
$password = trim($_POST['password']);
if (empty($username) === true || empty($password) === true) {
$errors[] = 'Sorry, but we need your username and password.';
} else if ($users->user_exists($username) === false) {
$errors[] = 'Sorry that username doesn\'t exists.';
} else if ($users->email_confirmed($username) === false) {
$errors[] = 'Sorry, but you need to activate your account. Please check your email.';
} else {
$login = $users->login($username, $password);
if ($login === false) {
$errors[] = 'Sorry, that username/password is invalid';
} else {
if (!isset($_SESSION['id']) && !empty($_COOKIE['RememberMeID']) && !empty($_COOKIE['RememberMeHash'])) {
$db->query("SELECT * FROM rememberMe WHERE userID = :userID AND userHash = :userHash");
$db->bind(':userID', $_COOKIE['RememberMeID']);
$db->bind(':userHash', $_COOKIE['RememberMeHash']);
$db->resultset();
$row = $db->rowCount();
if ($row['count'] > 0) {
$_SESSION['id'] = $login;
setcookie("RememberMeID", $_SESSION['id'], COOKIE_DURATION);
setcookie("RememberMeHash", $_COOKIE['RememberMeHash'], COOKIE_DURATION);
header('Location: home.php');
exit();
}
}
}
}
}
虽然,我想知道在哪里输入第一个代码以及在什么时间。实际上,必须在注册页面中插入插入令牌的代码,以便将注册用户输入数据库?