Laravel - 所有路由上的 NGINX + Apache 反向代理 404
Posted
技术标签:
【中文标题】Laravel - 所有路由上的 NGINX + Apache 反向代理 404【英文标题】:Laravel - NGINX + Apache reverse proxy 404 on all routes 【发布时间】:2018-06-14 08:11:16 【问题描述】:我正在 Laravel 中建立一个项目,它使用基于 Ubuntu 14.04 的自定义 vagrant box,并在典型的反向代理设置中运行 nginx 和 Apache。
现在,问题是沿途的某些东西没有注册 URL 路径,所以当我输入 http://mydomain.test/hello
时,我最终得到的只是另一端的 http://mydomain.test/index.php
,它似乎完全忘记了路线参数。
我正在使用带有 Mod PHP 的 Apache 2.4.7,Apache 配置如下。
<VirtualHost 127.0.0.1:8080>
ServerName application.test
ServerAlias www.application.test
DocumentRoot "/home/vagrant/application/public"
ErrorLog /var/log/apache2/error.log
CustomLog /var/log/apache2/access.log combined
<Directory "/home/vagrant/application/public">
Require all granted
AllowOverride all
</Directory>
</VirtualHost>
如图所示,Apache 正在监听 8080 端口,而 NGINX 正在使用以下配置监听 80 端口。
server
listen 80;
server_name application.test www.application.test;
root /home/vagrant/application/public;
index index.php index.html;
location /
try_files $uri $uri/ /index.php?$is_args$args;
location ~ \.php$
proxy_pass http://localhost:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
location ~ /\.
deny all;
我可以确认所有 Laravel 要求都得到满足,所以我有 MBString、OpenSSL 等...我还可以确认重写模块正在工作,因为我可以向我的 .htaccess
添加重定向子句,它确实如此按预期执行。
这是我的.htaccess
文件。
<IfModule mod_rewrite.c>
<IfModule mod_negotiation.c>
Options -MultiViews -Indexes
</IfModule>
RewriteEngine On
# Handle Authorization Header
RewriteCond %HTTP:Authorization .
RewriteRule .* - [E=HTTP_AUTHORIZATION:%HTTP:Authorization]
# Redirect Trailing Slashes If Not A Folder...
RewriteCond %REQUEST_FILENAME !-d
RewriteCond %REQUEST_URI (.+)/$
RewriteRule ^ %1 [L,R=301]
# Handle Front Controller...
RewriteCond %REQUEST_FILENAME !-d
RewriteCond %REQUEST_FILENAME !-f
RewriteRule ^ index.php [L]
</IfModule>
我可能在这里遗漏了什么吗?我之前配置过 NGINX 和 PHP-FPM,但这是我第一次使用 Apache,我遇到了多个类似的问题,但没有一个建议的修复对我有用,这就是我问这个问题的原因。
提前感谢您的帮助
编辑
一些进展。
如果我为 NGINX 设置位置配置如下
location /
proxy_pass http://localhost:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
然后它可以工作,但据我所知,这意味着即使是静态文件请求最终也会被代理到 Apache。
location ~ \.php$
似乎不起作用,因为我猜 laravel 漂亮的 url 不以“.php”后缀结尾。但是如何才能让这两个玩得很好呢?
我猜的想法是您有一个指向index.php
的默认位置,当触发该 index.php 文件时,nginx 会收到另一个与您的php
位置块匹配的 HTTP 请求,并将请求代理到 Apache .
问题在于,在第二次请求期间,所有关于 URI 的知识都丢失了,并且 URI 现在只是“index.php”,因此就 Apache 所知,您总是向 /index.php
发出请求。
我仍然不知道如何解决它。
【问题讨论】:
顺便说一下,我使用 Apache 的原因是服务器是这样配置的,我需要我的 Vagrant 配置与服务器紧密匹配。这就是为什么我要做整个 Apache 反向代理的事情,所以请不要只告诉我使用 PHP-FPM,因为我不能。 【参考方案1】:所以我想我已经想通了,如果你有类似的问题,一个可能的解决方案是将 $uri
变量添加到 try_files 指令
server
listen 80;
server_name application.test www.application.test;
root /home/vagrant/application/public;
index index.php index.html;
location /
try_files $uri $uri/ /index.php$uri;
location ~ \.php
proxy_pass http://localhost:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
location ~ /\.
deny all;
这样,当 nginx 调用你的 index.php 时,它会像 http://application.test/index.php/hello
一样调用它,这是 Apache 最终通过 PHP 接收和处理的 URL。
那么,.htaccess 开始发挥作用,Laravel 做到了,一切正常,这仍然只影响 PHP 文件,你的静态文件仍然应该由 NGINX 直接提供。
如果您发现此方法有任何问题,请告诉我。
更新
我后来犯了一个愚蠢的错误,让我相信还有其他问题,每条路由似乎都显示了我的“/”根路由的内容。 在尝试使用 Homestead 而不是我的自定义设置后,我惊讶地发现它也影响了 Homestead,因此它必须与我的应用程序本身相关,而不是与服务器相关。
基本上它是返回根视图的异常处理程序,因为我的请求丢失了我的 FormRequests 所需的一些数据,在更改我的异常处理程序类以处理 JSON 响应后,它按预期工作。
如果你落入这种陷阱,请尝试确保你的应用与 Homestead 兼容,如果可以,则说明你的 vagrant 设置有问题,如果没有,那就是你的 Laravel 应用有问题。
如果您的异常处理程序只是进行典型的渲染,那么请注意它会尝试重定向到上一个路由,如果您使用 Postman 开发 API,则该路由将是“/”。
【讨论】:
以上是关于Laravel - 所有路由上的 NGINX + Apache 反向代理 404的主要内容,如果未能解决你的问题,请参考以下文章
如何在 Laravel 4 中将一个路由重定向到 HTTPS,将所有其他路由重定向到 HTTP?