403 Forbidden表示服务器已定位资源但拒绝访问,主因分两类:一是系统级权限拒绝(文件/目录权限、SELinux、用户身份不匹配),二是应用层策略拦截(防盗链、Referer限制、IP白名单等);需先查Nginx错误日志定性,再针对性排查。

403 Forbidden 表示服务器已定位到资源,但明确拒绝提供访问——不是“找不到”,而是“不让你看”。它背后有两种典型成因:一种是系统级权限拒绝(文件/目录权限、SELinux、用户身份不匹配),另一种是应用层策略拦截(如防盗链、Referer 限制、IP 白名单等)。排查不能混为一谈,需先区分是“进不去”,还是“被拦下”。
看错误日志,快速定性是权限问题还是策略拦截
这是最不可跳过的一步。直接查 Nginx 错误日志:
- 运行 sudo tail -n 50 /var/log/nginx/error.log(或你站点配置的
error_log路径) - 若出现
(13: Permission denied),比如open() "/var/www/html/logo.png" failed (13: Permission denied),基本锁定为文件系统权限或 SELinux 问题 - 若出现
access forbidden by rule、client denied by server configuration或含referer、host关键词的提示,则大概率是防盗链、Referer 限制或 location 规则拦截
检查防盗链与 Referer 限制配置
防盗链常用 valid_referers + if ($invalid_referer) 组合实现,但容易误伤合法请求(如微信内嵌、APP WebView、空 Referer 测试):
- 确认配置中是否启用防盗链,例如:
valid_referers none blocked server_names *.example.com;<br>if ($invalid_referer) { return 403; } - 测试时用 curl 模拟不同 Referer:
curl -H "Referer: https://example.com" http://your.site/image.jpgcurl -H "Referer: https://bad-site.com" http://your.site/image.jpg - 注意:
none表示允许空 Referer(如直接输入 URL 访问),blocked表示 Referer 被代理篡改或加密的情况;漏配会导致正常访问也被拒
验证 Nginx 工作用户对资源的真实访问能力
别只看属主和 chmod,要模拟 Nginx 用户去读取:
- 查当前 worker 进程用户:
ps aux | grep "nginx: worker"(常见为nginx或www-data) - 逐级检查路径权限,重点看 执行(x)权限:
namei -l /var/www/html/image.jpg—— 它会显示/、/var、/var/www、/var/www/html每一级的属主、属组和权限 - 用该用户实际测试:
sudo -u www-data cat /var/www/html/image.jpg(成功说明权限通,失败则暴露具体哪一级卡住)
排查 SELinux 或 AppArmor 干预(尤其 CentOS/RHEL/Ubuntu)
传统权限全对,日志却报 (13: Permission denied)?很可能是安全模块在“静默拦截”:
- CentOS/RHEL:
sestatus看是否为enforcing;临时放行测试:sudo setenforce 0,再刷新页面。若恢复,就是 SELinux 导致 - 修复方式不是关 SELinux,而是打标签:
sudo chcon -R -t httpd_sys_content_t /var/www/html - Ubuntu:
aa-status | grep nginx查是否启用 AppArmor;拦截日志通常在/var/log/syslog或/var/log/audit/audit.log中搜avc: denied











