我最近从 Apache 切换到 Nginx。我是 Nginx 的新手,所以请多多包涵。我的一个应用程序使用第一个 URL 组件作为查询字符串,除非路径/文件存在 - 在这种情况下 Apache 会提供该文件。以前,我会将 URL 路径中的第一个字符串传递给 PHP,例如 example.com/foo(传递 foo)。我的旧 .htaccess 如下所示:
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
# if file or directory exists, serve it
RewriteCond %{REQUEST_FILENAME} -f [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule .* - [S=3]
# if not, pass the url component to PHP as the "section" query string
RewriteRule ^([^/]+)/?$ ?section=$1 [L]
</IfModule>
我在 Nginx 中尝试了很多东西,但因为我太新了,所以我陷入了困境。这似乎最接近我想要的:
server {
root /var/www/mysite.com;
index index.php;
server_name www.mysite.com mysite.com;
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php7.0-fpm.sock;
}
location / {
rewrite ^/(.*)$ /index.php?section=$1 break;
try_files $uri $uri/ /index.php$args;
}
}
但是,查询字符串似乎没有传递到我的index.php脚本。
我已经审查了以下其他问题:
- https://stackoverflow.com/questions/9641603/remove-parameters-within-nginx-rewrite (这不是我想要的,而是删除额外的 $args)
- https://stackoverflow.com/a/40334028/1171790(我尝试用空字符串替换“位置”来解决此问题,但它似乎没有将参数传递给 PHP)
- https://serverfault.com/a/488480/325456(我不清楚重写后我的正则表达式应该是什么。这个答案只使用了'^'。如果我仍然想提供我的静态文件/目录,这似乎太宽泛了)
- https://serverfault.com/a/542550/325456(这似乎最接近我想要的,但复制/粘贴代码并用我自己的替换文件名/值仍然对我没有作用)
如果有人比我更了解 Nginx,能够帮助我,我将永远感激不尽。
答案1
我最终用了一个命名位置。这个功能确实有用,但我仍然觉得还有更好的解决方案。
server {
root /var/www/mysite.com;
index index.php;
server_name mysite.com;
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php7.0-fpm.sock;
}
location / {
try_files $uri $uri/ @fallback;
}
location @fallback {
rewrite ^/(.*)$ /index.php?section=$1 last;
}
}
答案2
在 nginx 中执行此操作的更本地的方法是:
server {
root /var/www/mysite.com;
index index.php;
server_name example.com;
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php7.0-fpm.sock;
}
location /(.*) {
try_files $uri $uri/ /index.php?section=$1;
}