首先,我在localhost上测试。我有这个index.php文件,其中包含以下“记住我”复选框:
<input type="checkbox" id="login_remember" name="login_remember">
登录表单发布到loginvalidate.php,其中包含以下php脚本。我已经包含了很多注释来简化阅读代码的过程。请注意,我很确定下面的所有内容都能正常运行。
if (isset($_POST['login_submit'])) { //SETS VARIABLES FROM FORM
$email = $_POST[trim('login_email')];
$password = $_POST['login_password'];
$remember = isset($_POST['login_remember']) ? '1' : '0';
$db_found = mysqli_select_db($db_handle,$sql_database); //OPENING TABLE
$query = "SELECT password FROM registeredusers WHERE email = '$email'";
$result = mysqli_query($db_handle, $query) or die (mysqli_error($db_handle));
$row = mysqli_fetch_assoc($result);
$numrows = mysqli_num_rows($result);
if ($numrows!=0) //IF EMAIL IS REGISTERED
{
if ($row['password'] == $password) { //IF PASSWORD IN DATABASE == PASSWORD INPUT FROM FORM
if ($remember == '1'){ //IF USER WANTS TO BE REMEMBERED
$randomNumber = rand(99,999999); //RANDOM NUMBER TO SERVE AS A KEY
$token = dechex(($randomNumber*$randomNumber)); //CONVERT NUMBER TO HEXADECIMAL FORM
$key = sha1($token . $randomNumber);
$timeNow = time()*60*60*24*365*30; //STOCKS 30 YEARS IN THE VAR
$sql_database = "registeredusers";
$sql_table = "rememberme";
$db_found = mysqli_select_db($db_handle,$sql_database); //OPENING TABLE
$query_remember = "SELECT email FROM rememberme WHERE email = '$email'"; //IS THE USER IN TABLE ALREADY
$result = mysqli_query($db_handle, $query_remember) or die (mysqli_error($db_handle));
if (mysqli_num_rows($result) > 0) { //IF USER IS ALREADY IN THE REMEMBERME TABLE
$query_update = "UPDATE rememberme SET
email = '$email'
user_token = '$token'
token_salt = '$randomNumber'
time = '$timeNow'";
}
else { //OTHERWISE, INSERT USER IN REMEMBERME TABLE
$query_insert = "INSERT INTO rememberme
VALUES( '$email', '$token', '$randomNumber', '$timeNow' )";
}
setcookie("rememberme", $email . "," . $key, $timenow);
}
header('Location: homepage.php'); //REDIRECTS: SUCCESSFUL LOGIN
exit();
}
然后,当我关闭互联网浏览器并返回index.php时,我希望cookie自动连接用户。这是在我的index.php中:
include 'db_connect.php';
$sql_database = "registeredusers";
$db_found = mysqli_select_db($db_handle,$sql_database); //OPENING TABLE
session_start();
if (isset($_COOKIE['rememberme'])) {
$rememberme = explode(",", $_COOKIE["rememberme"]);
$cookie_email = $rememberme[0];
$cookie_key = $rememberme[1];
$query_remember = "SELECT * FROM rememberme WHERE email = '$cookie_email'"; //IS THE USER IN TABLE ALREADY
$result_remember = mysqli_query($db_handle, $query_remember) or die (mysqli_error($db_handle));
$row = mysqli_fetch_assoc($result_remember);
$token = $row['user_token'];
$randomNumber = $row['token_salt'];
$key = sha1($token . $randomNumber); //ENCRYPT TOKEN USING SHA1 AND THE RANDOMNUMBER AS SALT
if ($key == $cookie_key){
echo "lol";
}
}
问题是,它从不回应“大声笑”。此外,有没有人有任何关于如何连接用户的见解? AKA,这些内容应该是什么:
if ($key == $cookie_key){
echo "lol";
}
谢谢!我还是PHP和SQL的新手,所以如果我犯了一些初学者错误,请耐心等待。
编辑!:在我的代码中反复查看之后,我认为我的错误可能在于这些行。我不确定语法,以及我用来将值存储到$ token和$ randomNumber中的方法:
$query_remember = "SELECT * FROM rememberme WHERE email = '$cookie_email'"; //IS THE USER IN TABLE ALREADY
$result_remember = mysqli_query($db_handle, $query_remember) or die (mysqli_error($db_handle));
$row = mysqli_fetch_assoc($result_remember);
$token = $row['user_token'];
$randomNumber = $row['token_salt'];
答案 0 :(得分:21)
基本上有两种方法可以在PHP中实现登录脚本:
我将尝试在下面的原始表单中解释这两种用法,因此请记住,还有很多要了解它们。
简单地说,会话是唯一的,只要页面打开(或直到超时),它们就会存在。如果您的浏览器已关闭,会话也会发生同样的情况。
它们很容易实现。首先,确保在每个页面的开头开始会话:
<?php session_start(); ?>
注意:此调用在任何页面输出之前进行,这一点很重要,否则会导致“已发送标题”错误。
好的,现在您的会话已启动并正在运行。接下来做什么?这很简单:用户通过登录表单发送登录名/密码,然后验证它。如果登录有效,请将其存储到会话中:
if($validLoginCredentials){
$_SESSION['user_id'] = $id;
$_SESSION['user_login'] = $login;
$_SESSION['user_name'] = $name;
}
或作为数组(我更喜欢):
if($validLoginCredentials){
$_SESSION['user'] = array(
'name' => $name,
'login' => 'login',
'whichever_more' => $informationYouNeedToStore
);
}
好的,现在您的用户已登录。那么您如何知道/检查?只需检查用户的会话是否存在。
if(isset($_SESSION['user_id'])){ // OR isset($_SESSION['user']), if array
// Logged In
}else{
// Not logged in :(
}
当然,您可以更进一步,除了检查会话是否存在外,还要在数据库中搜索会话存储的用户ID以验证用户。这完全取决于您需要多少安全性。
在最简单的应用程序中,除非您在登录操作中手动设置,否则永远不会存在$ _SESSION ['user']。因此,只需检查它是否存在就会告诉您用户是否已登录。
登出:只需销毁它。你可以用
session_destroy();
但请记住,这会破坏您为该用户设置的所有会话。如果你还使用了$ _SESSION ['foo']和$ _SESSION ['bar'],那些也会消失。在这种情况下,只需取消设置特定会话:
unset($_SESSION['user']);
完成了!用户不再登录! :)
Cookie会在某些相似的会话中运行,除非它们存储在客户端浏览器中,并且只要您告诉它们就会持续。例如,当您将Cookie设置为在 $ timeNow 过期时,您将“使用Cookie作为会话”。
我通常不喜欢使用cookie进行简单登录,因为它们需要更高级的安全检查。由于它们存储在用户的浏览器中,因此很容易被操纵,恶意用户可以生成虚假登录信息并登录到您的系统。
就像你对会话一样。不同之处在于设置/取消设置cookie:
// To set a Cookie
// You could use the array to store several user info in one cookie
$user = array(
'id' => $id,
'name' => $name,
'login' => $login,
)
setcookie("loginCredentials", $user, time() * 7200); // Expiring after 2 hours
// Now to log off, just set the cookie to blank and as already expired
setcookie("loginCredentials", "", time() - 3600); // "Expires" 1 hour ago
要检查用户是否已登录,您可以使用与会话相同的示例,但使用其他变量:$ _COOKIE
if(isset($_COOKIE['user']['id'] && !empty(isset($_COOKIE['user']['id']))){
// Logged In
}else{
// Not logged in :(
}
嗯,就是这样。再次提醒您,这些是 非常简单的 登录方法示例。您需要更多地研究这两种方法,并根据应用程序的安全性要求,通过更多层次的安全检查来改进代码。
答案 1 :(得分:3)
你的代码背后的原因是
setcookie("rememberme", $email . "," . $key, $timenow); // this is getting expire exactly at same time when it is set
替换为
setcookie("rememberme", $email . "," . $key, time() * 3600);//expire after 1hour
答案 2 :(得分:0)
time()*60*60*24*365*30
这个时间大于 9999 年,你也不需要设置这个恐怖饼干时间。 您设置的 cookie 时间大于 9999 年,php 不允许此配置。 在我看来,最好的解决方案是设置新的过期 cookie 时间低于 9999 :))