指令说明
根据官网翻译的指令说明,括号中为翻译时添加的个人理解
语法: absolute_redirect on | off;
默认值: absolute_redirect on;
上下文: http, server, location
这个指令出现在版本 1.11.8.
如果关闭(指定为off),nginx发起的重定向是相对的(响应头Location中的URL)。请参考server_name_in_redirect和port_in_redirect指令。
语法: port_in_redirect on | off;
默认值: port_in_redirect on;
上下文: http, server, location
开启或关闭nginx发起绝对重定向(absolute_redirect on)时指定端口。重定向中首要主机名的使用由server_name_in_redirect指令控制。
语法: server_name_in_redirect on | off;
默认值: server_name_in_redirect off;
上下文: http, server, location
开启或关闭nginx将server_name指令指定的首要虚拟主机名用于发起的绝对重定向(absolute_redirect on)的功能。关闭此功能时(server_name_in_redirect off),nginx将使用“Host”请求头中的名字,如果没有此请求头,nginx将使用虚拟主机所在的IP地址。重定向中端口的使用由port_in_redirect指令控制。
实例演示
官网的指令说明比较简单,下面将结合nginx配置及请求示例详细说明。
这三个指令影响的是301、302跳转指定的URL为相对路径时,响应头Location字段,如果rewrite重写或return时的URL以“http://”或“https://”开头,则不受影响。
server {
listen 8080;
server_name www.mytest.com;
location /default/ {
absolute_redirect on;
port_in_redirect on;
server_name_in_redirect off;
rewrite ^(.*)$ /prefix$1 redirect;
}
location /port_off/ {
absolute_redirect on;
port_in_redirect off;
server_name_in_redirect off;
rewrite ^(.*)$ /prefix$1 redirect;
}
location /server_name_on/ {
absolute_redirect on;
port_in_redirect on;
server_name_in_redirect on;
rewrite ^(.*)$ /prefix$1 redirect;
}
location /absolute_off/ {
absolute_redirect off;
port_in_redirect on;
server_name_in_redirect on;
rewrite ^(.*)$ /prefix$1 redirect;
}
location /default_return/ {
absolute_redirect on;
port_in_redirect on;
server_name_in_redirect off;
return 302 /prefix$uri;
}
location /absolute/ {
absolute_redirect on;
port_in_redirect on;
server_name_in_redirect off;
rewrite ^(.*)$ http://test.test.com$1;
}
}
server {
listen 80;
server_name www.mytest.com;
location /default/ {
absolute_redirect on;
port_in_redirect on;
server_name_in_redirect off;
rewrite ^(.*)$ /prefix$1 redirect;
}
}
注:为避免浏览器或命令行程序发请求时自动携带Host请求头,文中示例用nc发起HTTP请求。
# echo -ne "GET /default/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://127.0.0.1:8080/prefix/default/index.html
默认配置下,如果请求没有Host头,则响应头Location的URL,包含IP和端口号(如果端口是80则不显示,见第10条)# echo -ne "GET /default/index.html HTTP/1.0\r\nHost: www.myexample.com\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://www.myexample.com:8080/prefix/default/index.html
默认配置下,如果请求中含有Host头,则响应头Location的URL使用Host的域名# echo -ne "GET /default/index.html HTTP/1.0\r\nHost: www.myexample.com:9000\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://www.myexample.com:8080/prefix/default/index.html
默认配置下,如果请求中含有Host头且Host头中包含端口,但响应头Location的URL依然使用请求时采用的端口号,而不是Host头中指定的端口号# echo -ne "GET /port_off/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://127.0.0.1/prefix/port_off/index.html
如果指定port_in_redirect off,则响应头Location的URL中没有端口号# echo -ne "GET /server_name_on/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://www.mytest.com:8080/prefix/server_name_on/index.html
如果指定server_name_in_redirect on,则响应头Location的URL的域名使用server_name指令指定的首要虚拟主机名# echo -ne "GET /server_name_on/index.html HTTP/1.0\r\nHost: www.myexample.com\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://www.mytest.com:8080/prefix/server_name_on/index.html
如果指定server_name_in_redirect on,即使请求中含有Host,响应头Location的URL的域名依然使用server_name指令指定的首要虚拟主机名# echo -ne "GET /absolute_off/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: /prefix/absolute_off/index.html
如果指定absolute_redirect off,则响应头Location的URL没有域名(IP)和端口号# echo -ne "GET /default_return/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://127.0.0.1:8080/prefix/default_return/index.html
类似第一条,return和rewrite的结果是一样的# echo -ne "GET /absolute/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 8080 | grep Location
Location: http://test.test.com/absolute/index.html
如果rewrite后的URL以“http://”或“https://”开头,则不受这三个指令影响# echo -ne "GET /default/index.html HTTP/1.0\r\n\r\n" | nc 127.0.0.1 80 | grep Location
Location: http://127.0.0.1/prefix/default/index.html
即使指定port_in_redirect on,当端口号是80时,响应头Location的URL中也不含有端口号,实际上HTTP默认端口就是80,对请求无影响。