diff --git a/.github/workflows/setup_env.sh b/.github/workflows/setup_env.sh index fa724895..427fdddf 100644 --- a/.github/workflows/setup_env.sh +++ b/.github/workflows/setup_env.sh @@ -24,7 +24,7 @@ kong-ngx-build \ --work $DOWNLOAD_ROOT \ --prefix $INSTALL_ROOT \ --openresty $OPENRESTY \ - --kong-nginx-module ${GITHUB_BASE_REF:-$GITHUB_REF_NAME} \ + --kong-nginx-module ${GITHUB_HEAD_REF:-$GITHUB_REF_NAME} \ --luarocks $LUAROCKS \ --openssl $OPENSSL \ --debug \ diff --git a/src/ngx_http_lua_kong_var.c b/src/ngx_http_lua_kong_var.c index aa0c14d4..ec36e5d4 100644 --- a/src/ngx_http_lua_kong_var.c +++ b/src/ngx_http_lua_kong_var.c @@ -18,6 +18,99 @@ #include "ngx_http_lua_kong_common.h" +/* default variable indexes will be loaded */ +static ngx_str_t default_vars[] = { + ngx_string("args"), + ngx_string("is_args"), + ngx_string("bytes_sent"), + ngx_string("content_type"), + /* ngx_string("host"), */ + + /* http request headers */ + ngx_string("http_authorization"), + ngx_string("http_connection"), + ngx_string("http_host"), + ngx_string("http_kong_debug"), + ngx_string("http_proxy"), + ngx_string("http_proxy_connection"), + ngx_string("http_te"), + ngx_string("http_upgrade"), + + /* http request headers */ + ngx_string("http_x_forwarded_for"), + ngx_string("http_x_forwarded_host"), + ngx_string("http_x_forwarded_path"), + ngx_string("http_x_forwarded_port"), + ngx_string("http_x_forwarded_prefix"), + ngx_string("http_x_forwarded_proto"), + + /* --with-http_ssl_module */ +#if (NGX_HTTP_SSL) + ngx_string("https"), +#endif + + /* --with-http_v2_module */ +#if (NGX_HTTP_V2) + ngx_string("http2"), +#endif + + /* --with-http_realip_module */ +#if (NGX_HTTP_REALIP) + ngx_string("realip_remote_addr"), + ngx_string("realip_remote_port"), +#endif + + /* ngx_string("remote_addr"), */ + ngx_string("remote_port"), + + /* ngx_string("request"), */ + ngx_string("request_length"), + ngx_string("request_method"), + ngx_string("request_time"), + ngx_string("request_uri"), + ngx_string("scheme"), + ngx_string("server_addr"), + ngx_string("server_port"), + +/* --with-http_ssl_module */ +#if (NGX_SSL) + ngx_string("ssl_cipher"), + ngx_string("ssl_client_raw_cert"), + ngx_string("ssl_client_verify"), + ngx_string("ssl_protocol"), + ngx_string("ssl_server_name"), +#endif + + ngx_string("upstream_http_connection"), + ngx_string("upstream_http_trailer"), + ngx_string("upstream_http_upgrade"), + ngx_string("upstream_status"), + + ngx_null_string +}; + + +static char * +ngx_http_lua_kong_load_default_var_indexes(ngx_conf_t *cf) +{ + ngx_str_t *var; + ngx_int_t index; + + for (var = default_vars; var->len; var++) { + index = ngx_http_get_variable_index(cf, var); + + if (index == NGX_ERROR) { + ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, + "unable to mark variable \"%V\" as indexed: no memory", + var); + return NGX_CONF_ERROR; + } + } + + return NGX_CONF_OK; +} + + char * ngx_http_lua_kong_load_var_index(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) { @@ -26,6 +119,10 @@ ngx_http_lua_kong_load_var_index(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) value = cf->args->elts; + if (ngx_strcmp(value[1].data, "default") == 0) { + return ngx_http_lua_kong_load_default_var_indexes(cf); + } + if (value[1].data[0] != '$') { ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "invalid variable name \"%V\"", &value[1]); @@ -93,12 +190,18 @@ ngx_http_lua_kong_ffi_var_get_by_index(ngx_http_request_t *r, ngx_uint_t index, vv = ngx_http_get_indexed_variable(r, index); if (vv == NULL || vv->not_found) { + ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, + "variable value is not found by index %d", index); + return NGX_DECLINED; } *value = vv->data; *value_len = vv->len; + ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, + "get variable value '%v' by index %d", vv, index); + return NGX_OK; } diff --git a/t/004-indexed-var.t b/t/004-indexed-var.t index 0510590f..0c48c658 100644 --- a/t/004-indexed-var.t +++ b/t/004-indexed-var.t @@ -3,7 +3,7 @@ use Test::Nginx::Socket::Lua; use Cwd qw(cwd); -plan tests => repeat_each() * (blocks() * 5); +plan tests => repeat_each() * (blocks() * 5) + 2; my $pwd = cwd(); @@ -106,6 +106,8 @@ GET /t value3 --- error_code: 200 +--- error_log +get variable value 'value3' by index --- no_error_log [error] [crit] @@ -145,6 +147,8 @@ GET /t value4_2 --- error_code: 200 +--- error_log +get variable value 'value4_2' by index --- no_error_log [error] [crit] diff --git a/t/005-indexed-var-openresty-suites.t b/t/005-indexed-var-openresty-suites.t index 392d0a62..d34e1b2b 100644 --- a/t/005-indexed-var-openresty-suites.t +++ b/t/005-indexed-var-openresty-suites.t @@ -9,7 +9,7 @@ use Test::Nginx::Socket::Lua; repeat_each(2); -plan tests => repeat_each() * (blocks() * 2 + 9); +plan tests => repeat_each() * (blocks() * 2 + 9 + 4); #no_diff(); #no_long_string(); @@ -40,6 +40,8 @@ GET /test --- response_body old: 32 new: nil +--- error_log +get variable value '32' by index @@ -64,6 +66,8 @@ GET /test?hello=world --- response_body old: hello=world new: nil +--- error_log +get variable value 'hello=world' by index @@ -164,6 +168,8 @@ invalid referer: --- no_error_log [error] +--- error_log +get variable value '' by index === TEST 7: false $invalid_referer variable value in Lua @@ -195,6 +201,8 @@ invalid referer: 1 --- no_error_log [error] +--- error_log +get variable value '1' by index === TEST 8: $proxy_host & $proxy_port & $proxy_add_x_forwarded_for @@ -350,4 +358,4 @@ variable not changeable --- pipelined_requests eval ["GET /balancer?port=8091", "GET /balancer?port=8092"] --- response_body eval -["this is backend peer 8091", "this is backend peer 8092"] \ No newline at end of file +["this is backend peer 8091", "this is backend peer 8092"] diff --git a/t/006-default_indexed-var.t b/t/006-default_indexed-var.t new file mode 100644 index 00000000..2ca6bdd1 --- /dev/null +++ b/t/006-default_indexed-var.t @@ -0,0 +1,413 @@ +# vim:set ft= ts=4 sw=4 et fdm=marker: +# modified from https://github.com/openresty/lua-nginx-module/blob/master/t/045-ngx-var.t +# with index always turned on +use Test::Nginx::Socket::Lua; + +#worker_connections(1014); +#master_process_enabled(1); +#log_level('warn'); + +repeat_each(2); + +plan tests => repeat_each() * (blocks() * 8) + 10; + +#no_diff(); +#no_long_string(); +#master_on(); +#workers(2); +run_tests(); + +__DATA__ + +=== TEST 1: sanity: directive works well +--- http_config + lua_kong_load_var_index default; + +--- config + location = /test { + content_by_lua_block { + ngx.say("ok") + } + } +--- request +GET /test +--- response_body +ok +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 2: variable $is_args, $args +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } + +--- config + location = /test { + content_by_lua_block { + ngx.say("var: ", ngx.var.is_args, ngx.var.args) + } + } +--- request +GET /test?hello=world +--- response_body +var: ?hello=world +--- error_log +get variable value '?' by index +get variable value 'hello=world' by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 3: variable $scheme, $host, $request_uri +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.scheme, " ", + ngx.var.host, " ", + ngx.var.request_uri) + } + } +--- request +GET /test +--- response_body +http localhost /test +--- error_log +get variable value 'http' by index +get variable value 'localhost' by index +get variable value '/test' by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 4: variable $http_xxx +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.http_authorization, " ", + ngx.var.http_connection, " ", + ngx.var.http_host, " ", + ngx.var.http_kong_debug, " ", + ngx.var.http_proxy, " ", + ngx.var.http_proxy_connection, " ", + ngx.var.http_te, " ", + ngx.var.http_upgrade + ) + } + } +--- request +GET /test +--- more_headers +authorization: auth +connection: close +host: test.com +kong-debug: 1 +proxy: 111 +proxy-connection: 222 +te: 333 +upgrade: 444 +--- response_body +auth close test.com 1 111 222 333 444 +--- error_log +get variable value 'auth' by index +get variable value 'close' by index +get variable value 'test.com' by index +get variable value '1' by index +get variable value '111' by index +get variable value '222' by index +get variable value '333' by index +get variable value '444' by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 5: variable $http_x_forwarded_xxx +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.http_x_forwarded_for, " ", + ngx.var.http_x_forwarded_host, " ", + ngx.var.http_x_forwarded_path, " ", + ngx.var.http_x_forwarded_port, " ", + ngx.var.http_x_forwarded_prefix, " ", + ngx.var.http_x_forwarded_proto + ) + } + } +--- request +GET /test +--- more_headers +x-forwarded-for: 111 +x-forwarded-host: 222 +x-forwarded-path: 333 +x-forwarded-port: 444 +x-forwarded-prefix: 555 +x-forwarded-proto: 666 +--- response_body +111 222 333 444 555 666 +--- error_log +get variable value '111' by index +get variable value '222' by index +get variable value '333' by index +get variable value '444' by index +get variable value '555' by index +get variable value '666' by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 6: request variables +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.request_method, " ", + ngx.var.request_length, " ", + ngx.var.request_uri, " ", + ngx.var.request_time, " ", + ngx.var.server_addr, " ", + ngx.var.server_port + ) + } + } +--- request +GET /test +--- response_body +GET 58 /test 0.000 127.0.0.1 1984 +--- error_log +get variable value 'GET' by index +get variable value '58' by index +get variable value '/test' by index +get variable value '0.000' by index +get variable value '127.0.0.1' by index +get variable value '1984' by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 7: upstream variables +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.upstream_http_connection, " ", + ngx.var.upstream_http_trailer, " ", + ngx.var.upstream_http_upgrade, " ", + ngx.var.upstream_status + ) + } + } +--- request +GET /test +--- response_body +nil nil nil nil +--- error_log +variable value is not found by index +variable value is not found by index +variable value is not found by index +variable value is not found by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 8: ssl/https variables +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.https, " ", + ngx.var.ssl_cipher, " ", + ngx.var.ssl_client_raw_cert, " ", + ngx.var.ssl_client_verify, " ", + ngx.var.ssl_protocol, " ", + ngx.var.ssl_server_name + ) + } + } +--- request +GET /test +--- response_body + nil nil nil nil nil +--- error_log +get variable value '' by index +variable value is not found by index +variable value is not found by index +variable value is not found by index +variable value is not found by index +variable value is not found by index +--- no_error_log +[error] +[crit] +[alert] + + + +=== TEST 9: reomte variables +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.remote_addr, " ", + ngx.var.remote_port + ) + } + } +--- request +GET /test +--- response_body_like +127.0.0.1 \d+$ +--- error_log +get variable value '127.0.0.1' by index +--- no_error_log +[error] +[crit] +[alert] + + +=== TEST 10: realip variables +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } + set_real_ip_from 127.0.0.1; + real_ip_header X-Real-IP; +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.remote_addr, " ", + ngx.var.realip_remote_addr, " ", + ngx.var.realip_remote_port + ) + } + } +--- request +GET /test +--- more_headers +X-Real-IP: 1.2.3.4 +--- response_body_like +^1.2.3.4 127.0.0.1 \d+$ +--- error_log +get variable value '1.2.3.4' by index +get variable value '127.0.0.1' by index +--- no_error_log +[error] +[crit] +[alert] + + +=== TEST 11: http2 variable +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } +--- config + location = /test { + content_by_lua_block { + ngx.say("http2:", ngx.var.http2) + } + } +--- request +GET /test +--- response_body +http2: +--- error_log +get variable value '' by index +--- no_error_log +[error] +[crit] +[alert] + +=== TEST 12: variable $content_type, $bytes_sent +--- http_config + lua_package_path "../lua-resty-core/lib/?.lua;lualib/?.lua;;"; + lua_kong_load_var_index default; + init_by_lua_block { + require("resty.kong.var").patch_metatable() + } + +--- config + location = /test { + content_by_lua_block { + ngx.say(ngx.var.content_type, " ", + ngx.var.bytes_sent) + } + } +--- request +GET /test +--- more_headers +content-type: plain +--- response_body +plain 0 +--- error_log +get variable value 'plain' by index +get variable value '0' by index +--- no_error_log +[error] +[crit] +[alert]