求助:攻击者如何绕过我的PHP 7.4 Web应用身份验证机制?
问题概述
- 我是准初级开发者,运营着多台线上服务器,其中一台基于PHP 7.4开发、由Bluehost托管的早期站点出现异常:陌生IP发起的请求占流量四分之一,多数因
loginCookie验证失败被重定向,但部分无Cookie的IP竟绕过验证,执行了管理员级的敏感数据库修改脚本 - 已做的补救:更新了存在漏洞的GuzzleHTTP库、封禁异常IP段、修改登录Cookie名称,但仍有新IP触发问题
现有实现细节
- 登录流程:用
prepared statements分步骤验证用户名密码,验证通过后设置loginCookie - 页面执行顺序:除登录页外,所有页面先跑业务代码(比如
Example-page.php先直接拼接$_COOKIE['login']插入数据库日志),再引入header.php;身份验证逻辑在header.php包含的nav.php里——业务代码跑在验证前面 - 验证规则:检查
loginCookie是否存在、长度是否符合要求,空值本应无法通过
核心问题定位
- 验证时机完全错误:这是最关键的漏洞。比如
Example-page.php里,日志插入操作直接用$_COOKIE['login'],还没等验证逻辑执行就跑完了——哪怕后续验证会重定向,已经执行的数据库操作没法撤销,等于攻击者直接绕过验证触发了敏感操作。 - Cookie验证的边界可能有问题:空Cookie本过不了长度校验,但如果代码里长度判断写了
>=0(而非>=最小有效长度),或者PHP自动把不存在的$_COOKIE['login']处理成空字符串,可能导致验证逻辑失效。 - 日志插入存在SQL注入风险:直接把
$_COOKIE['login']拼进SQL语句,哪怕是日志操作,攻击者也能构造恶意Cookie值破坏日志表,甚至以此为突破口进一步攻击。
修复方案
- 彻底调整执行顺序:所有受保护页面必须先跑身份验证,再执行任何业务代码(包括日志)。建议把验证逻辑抽成独立的
auth.php,在所有页面最顶部引入,验证不通过直接用exit()终止请求,不让后续代码有执行机会。 - 加固Cookie验证逻辑:
- 先严格判断
loginCookie是否存在:用isset($_COOKIE['login'])或者array_key_exists('login', $_COOKIE) - 校验长度要精准:比如生成的Cookie值是32位UUID,就判断
strlen($_COOKIE['login']) === 32,直接拒绝空值或长度不对的请求
- 先严格判断
- 日志插入改用
prepared statements:哪怕是日志,也不能直接拼用户输入,必须用预处理语句防注入 - 强化Cookie安全属性:
- 设置
HttpOnly属性,防止XSS窃取Cookie - 站点用HTTPS的话,加上
Secure属性,确保Cookie只通过HTTPS传输 - 配置
SameSite属性(比如Strict或Lax),防范CSRF攻击
- 设置
- 全量排查所有页面:确保所有涉及敏感操作的页面都把验证放在最开头,没有遗漏的业务代码跑在验证前面的情况
- 补充日志维度:把请求的完整Cookie、请求方法、参数都记进日志,方便定位攻击路径
内容的提问来源于stack exchange,提问作者flamencomori
相关产品推荐
相关产品推荐

