PHP 中如何使用 Session 实现用户登录与注销

Miles
Miles
发布时间:2026-10-14| 4人浏览过
原创

在 Web 开发中,利用 Session 维持用户登录状态是常见需求。本文将通过四个核心文件演示如何通过 PHP 和 MySQL 实现完整的用户登录、身份验证、页面保护及安全注销流程。

结果与目标

本教程旨在实现以下功能: - 用户输入用户名和密码进行登录。 - 服务端验证凭据并将用户信息存入 Session。

- 在受保护的页面上显示已登录状态并允许注销。
- 注销时彻底清除 Session 数据及相关的 Cookie,确保会话失效。

准备条件

  • 运行环境需支持 PHP 及 MySQL(或兼容的 SQL 数据库)。
  • 确保 PHP 已开启 session 模块。
  • 创建一个名为 mismatch_user 的数据库表,字段至少包含 user_id(主键)、username 和 password。

真实操作顺序

第1步:配置数据库连接

目的:集中管理数据库连接参数,方便后续调用,便于后期维护修改。

动作:创建 connectvars.php 文件,定义数据库主机、用户名、密码及数据库名称常量。

<?php
// 数据库的位置
define('DB_HOST', 'localhost');
// 用户名
define('DB_USER', 'root');
// 口令
define('DB_PASSWORD', '19900101');
// 数据库名
define('DB_NAME','test') ;
?>

重要参数: - DB_HOST: 通常设为 'localhost' 或 IP 地址。 - DB_PASSWORD: 请根据实际服务器设置修改,避免硬编码敏感信息在生产环境中。

第2步:构建登录逻辑与界面

目的:处理登录表单提交,验证用户凭证,若成功则初始化 Session。

入口:logIn.php

动作:

  1. 开启会话:使用 session_start() 启动 Session 机制。
  2. 检查状态:若 $_SESSION['user_id'] 已存在,说明已登录,直接重定向至登录成功页面。
  3. 处理提交:当收到 POST 请求时,获取用户名和密码,并进行防注入处理(如 mysqli_real_escape_string)。
  4. 查询数据库:构造 SQL 查询语句。原文示例使用了 SHA() 函数对密码进行单向加密后比对。请注意,虽然此处用于演示,但现代实践推荐迁移到更安全的哈希算法(如 password_hash)。
  5. 建立会话:若查询结果为一行记录,提取 user_id 和 username 存入 $_SESSION 数组。

代码实现:

<?php
// 插入连接数据库的相关信息
require_once 'connectvars.php';
// 开启一个会话
session_start();
$error_msg = "";

// 如果用户未登录,即未设置$_SESSION['user_id']时,执行以下代码
if(!isset($_SESSION['user_id'])){
    if(isset($_POST['submit'])){// 用户提交登录表单时执行如下代码
        $dbc = mysqli_connect(DB_HOST,DB_USER,DB_PASSWORD,DB_NAME);
        $user_username = mysqli_real_escape_string($dbc,trim($_POST['username']));
        $user_password = mysqli_real_escape_string($dbc,trim($_POST['password']));

        if(!empty($user_username)&&!empty($user_password)){
            // MySql中的SHA()函数用于对字符串进行单向加密
            $query = "SELECT user_id, username FROM mismatch_user WHERE username = '$user_username' AND "."password = SHA('$user_password')";
            // 用用户名和密码进行查询
            $data = mysqli_query($dbc,$query);
            // 若查到的记录正好为一条,则设置SESSION,同时进行页面重定向
            if(mysqli_num_rows($data)==1){
                $row = mysqli_fetch_array($data);
                $_SESSION['user_id']=$row['user_id'];
                $_SESSION['username']=$row['username'];
                $home_url = 'loged.php';
                header('Location: '.$home_url);
            }else{// 若查到的记录不对,则设置错误信息
                $error_msg = 'Sorry, you must enter a valid username and password to log in.';
            }
        }else{
            $error_msg = 'Sorry, you must enter a valid username and password to log in.';
        }
    }
}else{// 如果用户已经登录,则直接跳转到已经登录页面
    $home_url = 'loged.php';
    header('Location: '.$home_url);
}
?>
<html>
  <head>
    <title>Mismatch - Log In</title>
    <link rel="stylesheet" type="text/css" href="style.css" />
  </head>
  <body>
    <h3>Mismatch - Log In</h3>
    <!--通过$_SESSION['user_id']进行判断,如果用户未登录,则显示登录表单-->
    <?php
    if(!isset($_SESSION['user_id'])){
      echo '<p class="error">'.$error_msg.'</p>';
    ?>
    <!-- $_SERVER['PHP_SELF']代表用户提交表单时,调用自身php文件 -->
    <form method = "post" action="<?php echo $_SERVER['PHP_SELF'];<?php?>">
      <fieldset>
        <legend>Log In</legend>

        <label for="username">Username:</label>
        <!-- 如果用户已输过用户名,则回显用户名 -->
        <input type="text" id="username" name="username"
        value="<?php if(!empty($user_username)) echo $user_username; ?>" /

        <br/>

        <label for="password">Password:</label>
        <input type="password" id="password" name="password"/

      </fieldset>
      <input type="submit" value="Log In" name="submit"/
    </form>
    <?php
    }
    ?>
  </body>
</html>

完成状态:页面显示登录表单,用户提交正确凭证后会跳转至 loged.php。

第3步:验证登录状态

目的:保护需要登录后才能访问的页面,展示用户身份信息。

入口:loged.php

动作:

  1. 首先调用 session_start()。
  2. 检查 $_SESSION['username'] 是否存在。
  3. 若存在,输出欢迎信息及登出链接;否则应视为未登录(注:严格的生产环境应在每个受保护页面顶部检查并强制重定向回登录页)。

代码实现:

<?php
// 使用会话内存储的变量值之前必须先开启会话
session_start();
// 使用一个会话变量检查登录状态
if(isset($_SESSION['username'])){
  echo 'You are Logged as '.$_SESSION['username'].'<br/>';
  // 点击“Log Out”,则转到logOut页面进行注销
  echo '<a href="logOut.php"> Log Out('.$_SESSION['username'].')</a>';
}
/**
 * 在已登录页面中,可以利用用户的session如$_SESSION['username']、
 * $_SESSION['user_id']对数据库进行查询,可以做好多好多事情*/
?>

第4步:安全注销会话

目的:完全销毁会话数据,防止会话劫持或残留风险。

入口:logOut.php

动作:

  1. 启动会话:必须调用 session_start() 以访问当前会话变量。
  2. 清空数据:将 $_SESSION 设置为空数组,移除所有会话中的数据。
  3. 删除Cookie:如果浏览器存有会话 Cookie,通过 setcookie() 将其过期时间设为过去的时间,从而迫使浏览器删除它。
  4. 销毁会话:调用 session_destroy() 最终删除服务器端的会话文件。
  5. 重定向:使用 header() 将用户引导回登录页。

代码实现:

<?php
// 即使是注销时,也必须首先开始会话才能访问会话变量
session_start();
// 使用一个会话变量检查登录状态
if(isset($_SESSION['user_id'])){
  // 要清除会话变量,将$_SESSION超级全局变量设置为一个空数组
  $_SESSION = array();
  // 如果存在一个会话cookie,通过将到期时间设置为之前1个小时从而将其删除
  if(isset($_COOKIE[session_name()])){
    setcookie(session_name(),'',time()-3600);
  }
  // 使用内置session_destroy()函数调用撤销会话
  session_destroy();
}
// location首部使浏览器重定向到另一个页面
$home_url = 'logIn.php';
header('Location:'.$home_url);
?>

完成判断

用户可以成功登录,并在 loged.php 看到个人信息。点击 Logout 后,刷新 loged.php 将无法看到登录状态,且浏览器本地的 Session ID Cookie 被清除,标志着会话完全终结。

简要总结

以上就是如何使用 Session 实现用户登录、验证与安全注销的详细内容。该流程展示了 PHP 会话管理的基础核心:通过 session_start() 管理状态,利用 $_SESSION 存储关键标识,并在注销时严谨地清理内存与本地缓存。更多关于 PHP 会话安全优化的资料请关注本站其它相关文章!

相关标签:

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。