MVC框架下实现登录用户名与密码大小写敏感校验求助
解决MVC登录功能的大小写敏感校验问题
要实现用户名和密码的严格大小写校验,核心要解决两个问题:数据库默认查询不区分用户名大小写,以及原有代码的校验逻辑混乱。以下是具体修复方案:
1. 修改数据库用户名字段的排序规则
MySQL默认的utf8_general_ci/utf8mb4_general_ci排序规则不区分大小写,必须把user表的username字段改成区分大小写的排序规则,比如utf8mb4_bin(推荐支持全字符集)。
执行以下SQL语句修改表结构:
ALTER TABLE user MODIFY COLUMN username VARCHAR(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL;
_bin后缀的排序规则会直接按字符的二进制值比较,完全区分大小写。
2. 修正控制器的校验逻辑
原控制器存在重复调用模型方法、错误提示混淆的问题,修改后代码如下:
public function login() { if(isLoggedIn()) { header("Location: " . URLROOT . "/"); exit; // 跳转后终止脚本,避免后续代码执行 } $data = [ 'title' => 'Login page', 'username' => '', 'password' => '', 'usernameError' => '', 'passwordError' => '' ]; if($_SERVER['REQUEST_METHOD'] == 'POST'){ $_POST = filter_input_array(INPUT_POST); $data['username'] = trim($_POST['username']); $data['password'] = trim($_POST['password']); // 校验用户名 if(empty($data['username'])){ $data['usernameError'] = '请输入用户名。'; } else { // 查询用户(此时数据库已严格区分大小写) $user = $this->userModel->findUserByUsername($data['username']); if(!$user){ $data['usernameError'] = '用户名未注册或大小写输入错误。'; } } // 校验密码(仅当用户名有效时才校验) if(empty($data['password'])){ $data['passwordError'] = '请输入密码。'; } else if(isset($user)){ if(!password_verify($data['password'], $user->password)){ $data['passwordError'] = '密码错误,请重试。'; } } // 无错误则创建用户会话 if(empty($data['usernameError']) && empty($data['passwordError'])){ $this->createUserSession($user); } } $this->view('users/login', $data); }
改动说明:
- 移除冗余的重复查询,新增专门的
findUserByUsername方法查询用户 - 跳转后添加
exit,避免后续不必要的代码执行 - 调整校验顺序:先确认用户名存在且大小写正确,再校验密码,明确区分两类错误提示
- 避免在用户名无效时还校验密码,减少无效逻辑
3. 优化模型方法
在模型中新增findUserByUsername方法,并简化原login方法:
// 新增:根据用户名查询用户(严格区分大小写) public function findUserByUsername($username) { $this->db->query('SELECT * FROM user WHERE username = :username'); $this->db->bind(':username', $username); return $this->db->single(); } // 简化原login方法 public function login($username, $password) { $user = $this->findUserByUsername($username); return ($user && password_verify($password, $user->password)) ? $user : false; }
关键说明:
- 密码的大小写敏感是天然支持的:
password_hash和password_verify会严格保留密码的大小写信息,只要用户输入的密码和注册时完全一致(包括大小写),就能通过验证,无需额外处理 - 数据库排序规则是核心:如果不修改字段排序规则,即使代码逻辑正确,MySQL仍会忽略大小写查询用户,导致校验失效
内容的提问来源于stack exchange,提问作者Joh Gray
相关产品推荐
相关产品推荐

