mirror of
https://gitee.com/iresty/apisix.git
synced 2024-12-03 12:37:36 +08:00
feat(redirect): set redirect server port when enable http_to_https (#6686)
Signed-off-by: kwanhur <huang_hua2012@163.com> Co-authored-by: 罗泽轩 <spacewanderlzx@gmail.com>
This commit is contained in:
parent
ea3828afef
commit
32a8b8f6ba
@ -199,6 +199,7 @@ do
|
||||
upstream_cache_bypass = true,
|
||||
|
||||
var_x_forwarded_proto = true,
|
||||
var_x_forwarded_port = true,
|
||||
}
|
||||
|
||||
-- sort in alphabetical
|
||||
|
@ -24,6 +24,7 @@ local ipairs = ipairs
|
||||
local ngx = ngx
|
||||
local str_find = core.string.find
|
||||
local str_sub = string.sub
|
||||
local tonumber = tonumber
|
||||
|
||||
local lrucache = core.lrucache.new({
|
||||
ttl = 300, count = 100
|
||||
@ -147,6 +148,7 @@ function _M.rewrite(conf, ctx)
|
||||
core.log.info("plugin rewrite phase, conf: ", core.json.delay_encode(conf))
|
||||
|
||||
local ret_code = conf.ret_code
|
||||
local ret_port = tonumber(ctx.var["var_x_forwarded_port"])
|
||||
local uri = conf.uri
|
||||
local regex_uri = conf.regex_uri
|
||||
|
||||
@ -155,7 +157,12 @@ function _M.rewrite(conf, ctx)
|
||||
if conf.http_to_https and _scheme == "http" then
|
||||
-- TODO: add test case
|
||||
-- PR: https://github.com/apache/apisix/pull/1958
|
||||
uri = "https://$host$request_uri"
|
||||
if ret_port == nil or ret_port == 443 or ret_port <= 0 or ret_port > 65535 then
|
||||
uri = "https://$host$request_uri"
|
||||
else
|
||||
uri = "https://$host:" .. ret_port .. "$request_uri"
|
||||
end
|
||||
|
||||
local method_name = ngx.req.get_method()
|
||||
if method_name == "GET" or method_name == "HEAD" then
|
||||
ret_code = 301
|
||||
|
@ -45,6 +45,8 @@ The `redirect` Plugin can be used to configure redirects.
|
||||
|
||||
Only one of `http_to_https`, `uri` and `regex_uri` can be configured.
|
||||
|
||||
* When enabling `http_to_https`, the port in the redirect URL will be the value of header `X-Forwarded-Port` or the port of the server.
|
||||
|
||||
:::
|
||||
|
||||
## Enabling the Plugin
|
||||
@ -106,7 +108,6 @@ Content-Type: text/html
|
||||
Content-Length: 166
|
||||
Connection: keep-alive
|
||||
Location: /test/default.html
|
||||
|
||||
...
|
||||
```
|
||||
|
||||
@ -136,7 +137,6 @@ curl http://127.0.0.1:9080/hello -i
|
||||
HTTP/1.1 301 Moved Permanently
|
||||
...
|
||||
Location: https://127.0.0.1:9443/hello
|
||||
|
||||
...
|
||||
```
|
||||
|
||||
|
@ -32,19 +32,21 @@ description: 本文介绍了关于 Apache APISIX `redirect` 插件的基本信
|
||||
|
||||
## 属性
|
||||
|
||||
| 名称 | 类型 | 必选项 | 默认值 | 有效值 | 描述 |
|
||||
| ------------------- | ------------- | --------- | ------- | ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
||||
| http_to_https | boolean | 是 | false | [true,false] | 当设置为 `true` 并且请求是 HTTP 时,它将被重定向具有相同 URI 和 301 状态码的 HTTPS。 |
|
||||
| uri | string | 是 | | | 要重定向到的 URI,可以包含 NGINX 变量。例如:`/test/index.htm`, `$uri/index.html`,`${uri}/index.html`。如果你引入了一个不存在的变量,它不会报错,而是将其视为一个空变量。 |
|
||||
| regex_uri | array[string] | 是 | | | 将来自客户端的 URL 与正则表达式匹配并重定向。当匹配成功后使用模板替换发送重定向到客户端,如果未匹配成功会将客户端请求的 URI 转发至上游。 和 `regex_uri` 不可以同时存在。例如:["^/iresty/(.)/(.)/(.*)","/$1-$2-$3"] 第一个元素代表匹配来自客户端请求的 URI 正则表达式,第二个元素代表匹配成功后发送重定向到客户端的 URI 模板。 |
|
||||
| ret_code | integer | 是 | 302 | [200, ...] | HTTP 响应码 |
|
||||
| encode_uri | boolean | 是 | false | [true,false] | 当设置为 `true` 时,对返回的 `Location` Header 按照 [RFC3986](https://datatracker.ietf.org/doc/html/rfc3986)的编码格式进行编码。 |
|
||||
| append_query_string | boolean | 是 | false | [true,false] | 当设置为 `true` 时,将原始请求中的查询字符串添加到 `Location` Header。如果已配置 `uri` 或 `regex_uri` 已经包含查询字符串,则请求中的查询字符串将附加一个`&`。如果你已经处理过查询字符串(例如,使用 NGINX 变量 `$request_uri`),请不要再使用该参数以避免重复。 |
|
||||
| 名称 | 类型 | 必选项 | 默认值 | 有效值 | 描述 |
|
||||
|---------------------|---------------|-----|-------|--------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
|
||||
| http_to_https | boolean | 是 | false | [true,false] | 当设置为 `true` 并且请求是 HTTP 时,它将被重定向具有相同 URI 和 301 状态码的 HTTPS。 |
|
||||
| uri | string | 是 | | | 要重定向到的 URI,可以包含 NGINX 变量。例如:`/test/index.htm`, `$uri/index.html`,`${uri}/index.html`。如果你引入了一个不存在的变量,它不会报错,而是将其视为一个空变量。 |
|
||||
| regex_uri | array[string] | 是 | | | 将来自客户端的 URL 与正则表达式匹配并重定向。当匹配成功后使用模板替换发送重定向到客户端,如果未匹配成功会将客户端请求的 URI 转发至上游。 和 `regex_uri` 不可以同时存在。例如:["^/iresty/(.)/(.)/(.*)","/$1-$2-$3"] 第一个元素代表匹配来自客户端请求的 URI 正则表达式,第二个元素代表匹配成功后发送重定向到客户端的 URI 模板。 |
|
||||
| ret_code | integer | 是 | 302 | [200, ...] | HTTP 响应码 |
|
||||
| encode_uri | boolean | 是 | false | [true,false] | 当设置为 `true` 时,对返回的 `Location` Header 按照 [RFC3986](https://datatracker.ietf.org/doc/html/rfc3986)的编码格式进行编码。 |
|
||||
| append_query_string | boolean | 是 | false | [true,false] | 当设置为 `true` 时,将原始请求中的查询字符串添加到 `Location` Header。如果已配置 `uri` 或 `regex_uri` 已经包含查询字符串,则请求中的查询字符串将附加一个`&`。如果你已经处理过查询字符串(例如,使用 NGINX 变量 `$request_uri`),请不要再使用该参数以避免重复。 |
|
||||
|
||||
:::note
|
||||
|
||||
`http_to_https`、`uri` 和 `regex_uri` 只能配置其中一个属性。
|
||||
|
||||
* 当开启 `http_to_https` 时,重定向 URL 中的端口将是 `X-Forwarded-Port` 请求头的值或服务器的端口。
|
||||
|
||||
:::
|
||||
|
||||
## 启用插件
|
||||
|
108
t/plugin/redirect.t
vendored
108
t/plugin/redirect.t
vendored
@ -435,11 +435,59 @@ GET /hello
|
||||
Host: foo.com
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com:1984/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 19: redirect(pass well-known port 443 to x-forwarded-port)
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: foo.com
|
||||
x-forwarded-port: 443
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 19: enable http_to_https with ret_code(not take effect)
|
||||
=== TEST 20: redirect(pass negative number to x-forwarded-port)
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: foo.com
|
||||
x-forwarded-port: -443
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 21: redirect(pass number more than 65535 to x-forwarded-port)
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: foo.com
|
||||
x-forwarded-port: 65536
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 22: redirect(pass invalid non-number to x-forwarded-port)
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: foo.com
|
||||
x-forwarded-port: ok
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 23: enable http_to_https with ret_code(not take effect)
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -473,18 +521,18 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 20: redirect
|
||||
=== TEST 24: redirect
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: foo.com
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
Location: https://foo.com:1984/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 21: wrong configure, enable http_to_https with uri
|
||||
=== TEST 25: wrong configure, enable http_to_https with uri
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -519,7 +567,7 @@ qr/error_msg":"failed to check the configuration of plugin redirect err: value s
|
||||
|
||||
|
||||
|
||||
=== TEST 22: enable http_to_https with upstream
|
||||
=== TEST 26: enable http_to_https with upstream
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -558,18 +606,18 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 23: redirect
|
||||
=== TEST 27: redirect
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
Host: test.com
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://test.com/hello
|
||||
Location: https://test.com:1984/hello
|
||||
|
||||
|
||||
|
||||
=== TEST 24: set ssl(sni: test.com)
|
||||
=== TEST 28: set ssl(sni: test.com)
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -600,7 +648,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 25: client https request
|
||||
=== TEST 29: client https request
|
||||
--- config
|
||||
listen unix:$TEST_NGINX_HTML_DIR/nginx.sock ssl;
|
||||
|
||||
@ -674,7 +722,7 @@ close: 1 nil}
|
||||
|
||||
|
||||
|
||||
=== TEST 26: add plugin with new uri: /test/add
|
||||
=== TEST 30: add plugin with new uri: /test/add
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -709,46 +757,46 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 27: http to https post redirect
|
||||
=== TEST 31: http to https post redirect
|
||||
--- request
|
||||
POST /hello-https
|
||||
--- more_headers
|
||||
Host: test.com
|
||||
--- response_headers
|
||||
Location: https://test.com/hello-https
|
||||
Location: https://test.com:1984/hello-https
|
||||
--- error_code: 308
|
||||
--- no_error_log
|
||||
[error]
|
||||
|
||||
|
||||
|
||||
=== TEST 28: http to https get redirect
|
||||
=== TEST 32: http to https get redirect
|
||||
--- request
|
||||
GET /hello-https
|
||||
--- more_headers
|
||||
Host: test.com
|
||||
--- response_headers
|
||||
Location: https://test.com/hello-https
|
||||
Location: https://test.com:1984/hello-https
|
||||
--- error_code: 301
|
||||
--- no_error_log
|
||||
[error]
|
||||
|
||||
|
||||
|
||||
=== TEST 29: http to https head redirect
|
||||
=== TEST 33: http to https head redirect
|
||||
--- request
|
||||
HEAD /hello-https
|
||||
--- more_headers
|
||||
Host: test.com
|
||||
--- response_headers
|
||||
Location: https://test.com/hello-https
|
||||
Location: https://test.com:1984/hello-https
|
||||
--- error_code: 301
|
||||
--- no_error_log
|
||||
[error]
|
||||
|
||||
|
||||
|
||||
=== TEST 30: add plugin with new regex_uri: /test/1 redirect to http://test.com/1
|
||||
=== TEST 34: add plugin with new regex_uri: /test/1 redirect to http://test.com/1
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -787,7 +835,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 31: regex_uri redirect
|
||||
=== TEST 35: regex_uri redirect
|
||||
--- request
|
||||
GET /test/1
|
||||
--- response_headers
|
||||
@ -798,7 +846,7 @@ Location: http://test.com/1
|
||||
|
||||
|
||||
|
||||
=== TEST 32: regex_uri not match, get response from upstream
|
||||
=== TEST 36: regex_uri not match, get response from upstream
|
||||
--- request
|
||||
GET /hello
|
||||
--- error_code: 200
|
||||
@ -809,7 +857,7 @@ hello world
|
||||
|
||||
|
||||
|
||||
=== TEST 33: add plugin with new regex_uri: encode_uri = true
|
||||
=== TEST 37: add plugin with new regex_uri: encode_uri = true
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -849,7 +897,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 34: regex_uri redirect with special characters
|
||||
=== TEST 38: regex_uri redirect with special characters
|
||||
--- request
|
||||
GET /test/with%20space
|
||||
--- error_code: 200
|
||||
@ -861,7 +909,7 @@ Location: http://test.com/with%20space
|
||||
|
||||
|
||||
|
||||
=== TEST 35: add plugin with new uri: encode_uri = true
|
||||
=== TEST 39: add plugin with new uri: encode_uri = true
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -895,7 +943,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 36: redirect with special characters
|
||||
=== TEST 40: redirect with special characters
|
||||
--- request
|
||||
GET /hello/with%20space
|
||||
--- response_headers
|
||||
@ -906,7 +954,7 @@ Location: /hello/with%20space
|
||||
|
||||
|
||||
|
||||
=== TEST 37: add plugin with new uri: $uri (append_query_string = true)
|
||||
=== TEST 41: add plugin with new uri: $uri (append_query_string = true)
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -940,7 +988,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 38: redirect
|
||||
=== TEST 42: redirect
|
||||
--- request
|
||||
GET /hello?name=json
|
||||
--- response_headers
|
||||
@ -951,7 +999,7 @@ Location: /hello?name=json
|
||||
|
||||
|
||||
|
||||
=== TEST 39: add plugin with new uri: $uri?type=string (append_query_string = true)
|
||||
=== TEST 43: add plugin with new uri: $uri?type=string (append_query_string = true)
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -985,7 +1033,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 40: redirect
|
||||
=== TEST 44: redirect
|
||||
--- request
|
||||
GET /hello?name=json
|
||||
--- response_headers
|
||||
@ -996,7 +1044,7 @@ Location: /hello?type=string&name=json
|
||||
|
||||
|
||||
|
||||
=== TEST 41: enable http_to_https (pass X-Forwarded-Proto)
|
||||
=== TEST 45: enable http_to_https (pass X-Forwarded-Proto)
|
||||
--- config
|
||||
location /t {
|
||||
content_by_lua_block {
|
||||
@ -1036,7 +1084,7 @@ passed
|
||||
|
||||
|
||||
|
||||
=== TEST 42: enable http_to_https (pass X-Forwarded-Proto)
|
||||
=== TEST 46: enable http_to_https (pass X-Forwarded-Proto)
|
||||
--- request
|
||||
GET /hello
|
||||
--- more_headers
|
||||
@ -1044,4 +1092,4 @@ Host: foo.com
|
||||
X-Forwarded-Proto: http
|
||||
--- error_code: 301
|
||||
--- response_headers
|
||||
Location: https://foo.com/hello
|
||||
Location: https://foo.com:1984/hello
|
||||
|
Loading…
Reference in New Issue
Block a user