我使用默认的nginx Docker容器配置进行了简单的nginx容器设置,并将一个React构建加载到其中。对于大多数用例来说,这很完美,但是我遇到了一个古怪的现象,在我得到的新应用程序中(我没有写过)它不起作用,我想了解如何解决此问题以及为什么nginx正以这种方式工作。
当客户请求地址https://example.com/abc/def.html
时,他们会收到该页面,因为该页面存在。但是当他们请求https://example.com/abc/def
时,它重定向到http://<internal-docker-container-IP>/abc/def/
,但失败了,因为它在我的网络中无效。我知道IP和端口来自nginx配置,但是我不想为我部署的每个容器都重写它们,因为扩展性不好。
值得注意的是,nginx在此所做的所有操作都是在路径后添加斜杠,但同时也会重写主机和端口。我以为可以自己创建一个重写规则来添加尾部斜杠,但是似乎在执行过程中为时已晚。
在调试时,我尝试为著名的Web搜索引擎设置全局重写规则。我发现,在所有情况下,URL都没有重定向,除非URL没有斜杠。在那种情况下,我最终转到容器IP并获得连接超时。这对我来说似乎很奇怪。感觉好像有一个重写规则是在我的配置被点击之前触发的,但是我在配置中看不到它。
这是我的nginx.conf
:
worker_processes 1;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
include /etc/nginx/conf.d/*.conf;
}
这是唯一包含的* .conf文件。这是容器的默认设置,除了我在第7行添加了重写:
listen 80;
server_name localhost;
#charset koi8-r;
#access_log /var/log/nginx/host.access.log main;
rewrite ^.*$ https://www.myforcedredirectfordebugpurposes.com redirect;
location / {
root /usr/share/nginx/html;
index index.html index.htm;
}
#error_page 404 /404.html;
# redirect server error pages to the static page /50x.html
#
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root /usr/share/nginx/html;
}
# proxy the PHP scripts to Apache listening on 127.0.0.1:80
#
#location ~ \.php$ {
# proxy_pass http://127.0.0.1;
#}
# pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
#
#location ~ \.php$ {
# root html;
# fastcgi_pass 127.0.0.1:9000;
# fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
# include fastcgi_params;
#}
# deny access to .htaccess files, if Apache's document root
# concurs with nginx's one
#
#location ~ /\.ht {
# deny all;
#}
}
我觉得重定向应该总是触发-毕竟,它在所有路径上-但是当我转到https://example.com/abc/def
时,我最终遇到了失败的容器IP地址。如果我转到https://example.com/abc/def/
(请注意末尾的斜杠),则重定向有效。这不是很奇怪吗?有没有一种方法可以配置它,而无需我在配置中对Nginx容器的地址进行硬编码?我以前从来没有这样做。
答案 0 :(得分:0)
这可以通过在根try_files
块中使用location
指令来实现:
location / {
root /usr/share/nginx/html;
index index.html index.htm;
try_files $uri $uri.html $uri/;
}
在此额外的行中,传入的请求将首先尝试给定的URI,然后尝试添加了.html
的URI,最后尝试了添加了/
的URI。它将请求转发到第一个匹配项,而不显示给浏览器(因此浏览器不需要显示转发的地址)。
对于以前在末尾使用.html
或以斜杠结尾的链接,是因为这些是Web服务器的有效uri:.html
文件存在于这些路径中,并且由于行index index.html index.htm
,尾部的斜杠表示隐式索引文件,因此nginx从目录内返回该文件。
我仍然不确定为什么我尝试的URL重写不起作用,但是获得所需的结果并不需要解决此问题,这是为了避免在其中指定服务器名称和端口配置。