本文目录导读:

- 核心概念:什么是“敏感数据”?
- 静态代码扫描(白盒发现)—— 最主流方法
- 动态扫描(黑盒发现)—— 找运行时的输出
- 日志与流量审计(被动发现)
- 针对 PHP 特有的高级发现技巧
- 具体操作流程(SOP 参考)
- 总结推荐组合打法
PHP 敏感数据发现通常指在代码中扫描、识别和定位可能泄露敏感信息的代码片段,常见于安全审计、等保测评、DevSecOps 流程中。
这里分几个层面给出具体的发现方法和工具链:
核心概念:什么是“敏感数据”?
在 PHP 代码中,我们主要关注四类:
- 硬编码凭据:数据库密码、API Key、支付宝/微信支付密钥、SMTP 密码、JWT Secret。
- 个人信息(PII):身份证号、手机号、银行卡号、家庭住址、健康记录。
- 敏感配置:云存储 Bucket 链接、服务器内网 IP、调试开关(如
APP_DEBUG=true、display_errors=On)。 - 内部逻辑泄露:目录遍历路径、备份文件(
.sql、.bak)、phpinfo()或var_dump()输出未做访问控制。
静态代码扫描(白盒发现)—— 最主流方法
这是最常用的方式,不需要运行代码,直接扫描源码。
专业商业工具
- Fortify SCA(Micro Focus):静态应用安全测试(SAST)界的标杆,能识别复杂数据流(如
$_POST输入直接拼入mysql_query),规则库庞大,误报率相对低。 - Checkmarx:擅长从“输入点”追踪到“敏感操作点”的污点追踪(Taint Analysis),能发现“数据写到日志”这类问题。
- SonarQube(社区版/开发者版):扫描规则里内置了“硬编码密码(Hardcoded Credentials)”和“加密算法不牢靠”等规则,免费版足够用。
开源免费工具(推荐使用)
| 工具名称 | 主要用途 | 特点 |
|---|---|---|
| Semgrep | 通用代码安全扫描 | 强力推荐,基于规则模式匹配,速度快,规则可自定义(.yml),社区有现成的 PHP 敏感数据规则包。 |
| PHPStan / Psalm | 静态类型分析 | 主要查逻辑错误,但可以通过自定义扩展(Stubs)来追踪敏感变量的流向。 |
| RIPS(已停维护) | 曾经的 PHP 扫描王者 | 代码可用,但只支持 PHP 5.x 时代,现在不建议在新项目用。 |
| gitleaks / trufflehog | 专门扫密钥/令牌 | 不一定只针对 PHP,但它能通过正则和熵检测(Entropy),直接在 Git 历史里找出暴露的密码和 Token。 |
手动正则/命令行发现(轻量快速排查)
在服务器或 CI 环境直接运行 grep:
# 1. 查找硬编码密码(常见赋值模式)
grep -rnE "\b(password|passwd|pwd|secret)\b\s*=" --include="*.php" /var/www/html/
# 2. 查找数据库连接(常见函数)
grep -rn "mysql_connect\|mysqli_connect\|new PDO" --include="*.php" /var/www/html/
# 3. 查找常见第三方API密钥(阿里云/腾讯云/AWS)
grep -rnE "AKIA[0-9A-Z]{16}|LTAI[0-9A-Z]{12,}" --include="*.php" /
# 4. 查找开启的调试和报错(潜在信息泄露)
grep -rn "display_errors\s*=\s*On\|APP_DEBUG\s*=\s*true" --include="*.php" /var/www/html/
动态扫描(黑盒发现)—— 找运行时的输出
静态扫描找“代码里的问题”,动态扫描找“跑起来后泄露了什么”。
- 接口响应抓取:
- 使用 Burp Suite 或抓包工具。
- 重点查看
/api/v1/user/detail或admin.php等接口。 - 关注点:JSON 响应中是否多于客户端需要的字段(比如返回了
password_hash、id_card、phone)。
- 错误页探测:
- 篡改请求参数使其报错(例如发送 100 万个字符到
int字段)。 - 如果开启了
display_errors,PHP 会把绝对路径、数据库连接参数、甚至 SQL 片段打出来。
- 篡改请求参数使其报错(例如发送 100 万个字符到
- 文件泄露探测:
- 尝试访问
/.git/、/.env、/config/database.php.bak、/.sql备份文件。 - 发送
?debug=1参数看是否会触发var_dump()。
- 尝试访问
日志与流量审计(被动发现)
- 数据库日志:查看 MySQL 慢查询日志或常规
log,看是否记录了完整的 SQL(里面可能包含未脱敏的手机号)。 - Web 访问日志:检查
access.log中是否有人通过?user=13800000000这种 GET 方式传参(URL 里的 PII 比 POST 更危险,因为会进入日志)。 - 框架日志:Laravel 的
storage/logs/中,排查异常抛出时是否将$request->all()或$password原样写入。
针对 PHP 特有的高级发现技巧
这一条建议单独看,PHP 环境有特定的泄露路径:
.git泄露:如果项目根目录有.git文件夹且被 web 服务器解析,可以用GitHack或git-dumper直接恢复源码,密码可能藏在历史提交里。phpinfo()探测:如果代码里有phpinfo()且未做 IP 限制,会直接把$_SERVER、$_ENV和加载的扩展路径全打出来(包含数据库主机名、源代码路径)。extract()与变量覆盖:如果代码用了extract($_GET),攻击者可能通过构造参数覆盖掉硬编码的$password变量。- 反序列化漏洞:对
unserialize()的入参未过滤,可能导致在__destruct()方法中输出敏感类属性。
具体操作流程(SOP 参考)
如果你需要写一个“敏感数据发现”的脚本,建议按此顺序:
// 伪代码逻辑示意
$scanDir = '/var/www/html';
$rules = [
'sql_password' => '/("password"|db_pass)\s*=>\s*["\']([^"\']+)["\']/i',
'api_key' => '/(sk-live-|pk-live-|AKIA|AIza[0-9A-Za-z_-])/',
'手机号' => '/(1[3-9]\d{9})/', // 注意国内手机号正则
];
$iterator = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($scanDir));
foreach ($iterator as $file) {
if ($file->getExtension() !== 'php') continue;
$content = file_get_contents($file->getPathname());
foreach ($rules as $type => $pattern) {
if (preg_match_all($pattern, $content, $matches, PREG_OFFSET_CAPTURE)) {
echo "[高危] 文件: {$file->getPathname()} 发现类型: {$type} 位置: 第" . $line . "行\n";
}
}
}
总结推荐组合打法
| 场景 | 推荐工具 | 目的 |
|---|---|---|
| 上线前 CI 集成 | Semgrep + GitLeaks | 阻断硬编码密码提交,发现代码中的敏感调用。 |
| 存量大项目审计 | SonarQube 或 Fortify | 生成完整的漏洞报告,人工核查。 |
| 应急排查 | grep 正则在服务器直接搜 |
快速定位某个测试密钥或硬编码密码的分布。 |
| 运行期防泄露 | Burp Suite / 清理日志 | 确保响应体不携带额外 PII,日志不落明文。 |
注意:扫描出来的高概率“敏感信息”需要人工复核,很多账号密码可能是测试数据或加密后的密文,需人工判断是否为真实生产密钥,若发现敏感数据,建议配合 git-filter-repo 清理 Git 历史,并强制轮换现有密钥。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播