我在Nginx $request_body变量中匹配特定单词时遇到问题.
如果正文请求中有特殊字,我想代理传递,
所以我的方法是这样的:
location ~ \.PHP${
if ($request_body ~* (.*)) {
proxy_pass http://test.proxy;
break;
}
# other case...
}
这匹配所有内容,if语句有效,
但如果我以任何方式更改正则表达式,我都无法获得成功.
所以现在我的问题是:
我如何正确定义Nginx中的正则表达式以匹配,例如“目标”?
提前致谢!
最佳答案
您的代码有很多问题.
>“($request_body~ *(.*))”永远不会匹配其他人所说的任何内容,因此“其他案例”始终是结果
>更重要的是,它使用“proxy_pass”和“if”这是典型的邪恶. http://wiki.nginx.org/IfIsEvil.
要获得您想要的,请使用第三方ngx_lua模块(v0.3.1rc24及更高版本)…
location ~ \.PHP${
rewrite_by_lua '
ngx.req.read_body()
local match = ngx.re.match(ngx.var.request_body,"target")
if match then
ngx.exec("@proxy");
else
ngx.exec("@other_case");
end
';
}
location @proxy {
# test.proxy stuff
...
}
location @other_case {
# other_case stuff
...
}
你可以在https://github.com/chaoslawful/lua-nginx-module/tags获得ngx_lua.
PS.请记住,lua的重写总是在Nginx重写指令之后执行,所以如果你在其他情况下放置任何这样的指令,它们将首先被执行,你将获得有趣的东西.
您应该将所有重写放在lua上下文的重写中,以获得一致的结果.这就是“其他案例”的“if..else..end”安排的原因.
您可能需要这个更长的版本
location ~ \.PHP${
rewrite_by_lua '
--request body only available for POST requests
if ngx.var.request_method == "POST"
-- Try to read in request body
ngx.req.read_body()
-- Try to load request body data to a variable
local req_body = ngx.req.get_body_data()
if not req_body then
-- If empty,try to get buffered file name
local req_body_file_name = ngx.req.get_body_file()
--[[If the file had been buffered,open it,read contents to our variable and close]]
if req_body_file_name then
file = io.open(req_body_file_name)
req_body = file:read("*a")
file:close()
end
end
-- If we got request body data,test for our text
if req_body then
local match = ngx.re.match(req_body,"target")
if match then
-- If we got a match,redirect to @proxy
ngx.exec("@proxy")
else
-- If no match,redirect to @other_case
ngx.exec("@other_case")
end
end
else
-- Pass non "POST" requests to @other_case
ngx.exec("@other_case")
end
';
}