Nginx location 优先级与上传目录拦截
TOPIC SOURCE
WordPress 上传目录防 PHP 执行:Nginx 与 PHP-FPM 的检查、整改和回滚清单
上传目录的拦截规则已经写进 Nginx 配置,上传的 PHP 文件却仍可能进入 PHP-FPM。问题往往不在于有没有写“禁止访问”,而在于请求最终命中了哪个 location。对 WordPress 站点,目标也不是封禁整个 wp-content/uploads:图片和附件仍需正常访问,应阻断的是该目录中的 PHP 类请求进入解释器,同时避免脚本源码被当作静态文件返回。
判断规则是否有效,先要确认实际上传文件路径与访问 URL 的映射,再查看站点当前加载的 server 配置。默认的 /wp-content/uploads/ 不能代替核实:定制上传路径、多站点目录或 alias 映射,都可能让规则保护错位置。随后找出通用 PHP 正则 location 及其 fastcgi_pass,比较它与上传目录拒绝规则的匹配范围和顺序。多个正则规则都可能匹配同一请求时,先匹配到的规则会影响处理结果;因此,针对上传路径的拒绝规则必须先于通用 PHP 处理规则。
单独使用 ^~ 前缀规则也不能直接视为安全:它会影响后续正则匹配,如果上传目录中的脚本因此被静态返回,虽然没有执行,源码仍可能暴露。拒绝规则还应覆盖站点实际允许进入 PHP 处理流程的扩展名及路径形式,而不是只检查一种以 .php 结尾的 URL。
变更前备份配置,修改后先检查语法,再重载 Nginx。验证时同时看两边:已知图片能否访问、后台能否继续上传;上传目录中的无害测试脚本请求是否被拒绝,响应中既无执行结果也无源码,并结合日志确认请求没有进入 PHP-FPM。只有这些结果一致,才能说明拦截生效,而不只是配置文件里出现了一条拒绝规则。

参与讨论
之前只盯着有没有执行,源码暴露这点真容易漏