upstream test {
server ip1:port1;
server ip1:port2;
server ip1:port3;
server ip1:port4;
}
location / {
set $dst test;
proxy_pass http://$dst;
}
接近-
最初在数据库中,我将上游块中每个上游IP的请求计数存储为零。
当向 Nginx 发出请求时,我获取 proxy_pass 使用的上游 IP,然后对数据库执行 ngx.location.capture 子请求以增加上游 IP 的计数。
但是如何在 proxy_pass 之后执行 ngx.location.capture 呢?
还有其他方法可以实现这一目标吗?
有人可以帮我吗?
我认为 proxy_pass 之后意味着您不希望数据库减慢对客户端的响应速度。
在Directives下的官方参考中,您可以看到“Log Phase”是发送数据的内容阶段之后进入的最后一个阶段。正如参考还告诉,在日志阶段执行的代码没有机会更改内容(因为它已经发送了)。
第二个限制是没有可用的
ngx.location.capture
。所以你的数据库基本上必须通过 lua 代码来更新,而不是通过运行子请求来更新。
使用LuaSQLite3的基本思想:
upstream test {
server ip1:port1;
server ip1:port2;
server ip1:port3;
server ip1:port4;
}
location / {
set $dst test;
proxy_pass http://$dst;
log_by_lua_block {
local sqlite3 = require("lsqlite3")
local db = sqlite3.open('access_list.sqlite3')
db:exec([[
CREATE TABLE logs (
backend VARCHAR NOT NULL PRIMARY KEY,
access INTEGER NOT NULL DEFAULT 1
);
]])
local prep = db:prepare('INSERT INTO logs(backend) VALUES (:backend) ON CONFLICT(backend) DO UPDATE SET access=access+1')
prep:bind_names({ backend = ngx.var.dst })
prep:step()
prep:reset()
db:close()
}
}
如果在openresty的init阶段启动db连接,可以在这里进一步优化。