You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@apisix.apache.org by GitBox <gi...@apache.org> on 2021/07/26 11:39:15 UTC
[GitHub] [apisix] philzhangrui opened a new issue #4675: request help: Write your own plug-ins to improve performance
philzhangrui opened a new issue #4675:
URL: https://github.com/apache/apisix/issues/4675
### Issue description
I wrote a plug-in myself. In the access phase, add 1 to the number of requests in redis, and then return the error code. Each execution takes more than 1 second. I want to know why
local core = require("apisix.core")
local plugin_name = "limit-conn-ext"
local redis_new = require("resty.redis").new
local ngx = ngx
local code
local script = [=[
if redis.call('ttl', KEYS[1]) < 0 then
redis.call('set', KEYS[1], ARGV[1] - 1, 'EX', ARGV[2])
return ARGV[1] - 1
end
return redis.call('incrby', KEYS[1], -1)
]=]
local lrucache = core.lrucache.new({
type = "plugin",
})
local schema = {
type = "object",
properties = {
-- 请求通过数
conn = {type = "integer", exclusiveMinimum = 0},
--排队数
burst = {type = "integer", minimum = 0},
--排队等待时间
default_conn_delay = {type = "number", exclusiveMinimum = 0},
key = {type = "string" },
-- 超过排队返回码
rejected_code = {
type = "integer", minimum = 200, maximum = 599, default = 503
},
--单位时间
time_window = {type = "integer", exclusiveMinimum = 0},
policy = { type = "string" }
},
required = {"conn", "burst", "default_conn_delay", "key"},
dependencies = {
policy = {
oneOf = {
{
properties = {
policy = {
enum = {"redis"},
},
redis_host = {
type = "string", minLength = 2
},
redis_port = {
type = "integer", minimum = 1, default = 6379,
},
redis_password = {
type = "string", minLength = 0,
},
redis_database = {
type = "integer", minimum = 0, default = 0,
},
redis_timeout = {
type = "integer", minimum = 1, default = 1000,
},
},
required = {"redis_host"},
},
{
properties = {
policy = {
enum = {"redis-cluster"},
},
redis_cluster_nodes = {
type = "array",
minItems = 2,
items = {
type = "string", minLength = 2, maxLength = 100
},
},
redis_password = {
type = "string", minLength = 0,
},
redis_timeout = {
type = "integer", minimum = 1, default = 1000,
},
redis_cluster_name = {
type = "string",
},
},
required = {"redis_cluster_nodes", "redis_cluster_name"},
}
}
}
}
}
local _M = {
version = 0.1,
priority = 1004,
name = plugin_name,
schema = schema,
}
function _M.check_schema(conf)
local ok, err = core.schema.check(schema, conf)
if not ok then
return false, err
end
return true
end
function _M.access(conf, ctx)
local red = redis_new()
local timeout = conf.redis_timeout or 1000 -- 1sec
red:set_timeouts(timeout, timeout, timeout)
local ok, err = red:connect(conf.redis_host, conf.redis_port or 6379)
if not ok then
return false, err
end
local count
count, err = red:get_reused_times()
if 0 == count then
if conf.redis_password and conf.redis_password ~= '' then
local ok, err = red:auth(conf.redis_password)
if not ok then
return nil, err
end
end
-- select db
if conf.redis_database ~= 0 then
local ok, err = red:select(conf.redis_database)
if not ok then
return false, "failed to change redis db, err: " .. err
end
end
elseif err then
-- core.log.info(" err: ", err)
return nil, err
end
local key = ctx.var["uri"]
core.log.warn("limit key: ", key)
core.log.warn("limit conn: ", conf.conn)
core.log.warn("limit conf.time_window: ", conf.time_window)
local remaining, err = red:eval(script, 1, key, conf.conn, conf.time_window)
core.log.warn("remaining:",remaining)
if err then
return nil, err
end
if remaining < 0 or remaining == 0 then
local queueKey = key.."queue"
--看队列长度是否已满,
local queueSize = red:llen(queueKey)
core.log.warn("queueSize:",queueSize)
if queueSize ==0 or queueSize <conf.burst then
local value = key .."|"..ngx.now()*1000
local size,error = red:lpush(queueKey,value);
core.log.warn("addQueueSize:",size)
if not error then
--加入队列失败
code = 202;
end
--加入队列
code = 203
else
-- 队列已满
code = 201
end
else
-- 直接通过
code = 200
end
local ok, err = red:set_keepalive(10000, 100)
if not ok then
core.log.error("limit-conn-ext error",err)
return nil, err
end
end
function _M.body_filter(conf, ctx)
ngx.arg[1] = code
ngx.arg[2] = true
end
return _M
### Environment
Request help without environment information will be ignored or closed.
* apisix version (cmd: `apisix version`):
* OS (cmd: `uname -a`):
* OpenResty / Nginx version (cmd: `nginx -V` or `openresty -V`):
* etcd version, if have (cmd: run `curl http://127.0.0.1:9090/v1/server_info` to get the info from server-info API):
* apisix-dashboard version, if have:
* luarocks version, if the issue is about installation (cmd: `luarocks --version`):
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org
[GitHub] [apisix] philzhangrui closed issue #4675: request help: Write your own plug-ins to improve performance
Posted by GitBox <gi...@apache.org>.
philzhangrui closed issue #4675:
URL: https://github.com/apache/apisix/issues/4675
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: notifications-unsubscribe@apisix.apache.org
For queries about this service, please contact Infrastructure at:
users@infra.apache.org