xfy 6543422281 docs: 添加 Nginx 配置和 Lua 脚本示例文档
- config: 反向代理、缓存、负载均衡、安全、SSL 等配置模板
- lua: API 网关、认证、动态路由、限流、WebSocket 等脚本示例

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-10 17:59:22 +08:00

97 lines
2.3 KiB
Lua
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

-- metrics.lua
-- 请求耗时统计与指标收集
local M = {}
local shared
--- 初始化 metrics 模块
-- @param shared_dict nginx shared dict通过 lua_shared_dict 创建)
function M.init(shared_dict)
shared = shared_dict
end
--- 原子递增计数器
-- @param key 指标键
-- @param delta 增量(默认 1
local function incr(key, delta)
local newval, err = shared:incr(key, delta or 1)
if not newval then
-- key 不存在,初始化为 0 再递增
shared:add(key, 0)
shared:incr(key, delta or 1)
end
end
--- 更新请求耗时统计
-- 在 log_by_lua 阶段调用
-- @param ngx_obj nginx 上下文对象
function M.observe(ngx_obj)
if not shared then
return
end
local status = ngx_obj.status or 0
local uri = ngx_obj.var.uri or "unknown"
local method = ngx_obj.var.request_method or "UNKNOWN"
local request_time = tonumber(ngx_obj.var.request_time) or 0
local prefix = method .. ":" .. uri
-- 总请求数
incr("req:total", 1)
-- 按状态码分组
local status_group = math.floor(status / 100) .. "xx"
incr("req:" .. status_group, 1)
-- 按路径+状态码分组
incr("req:" .. prefix .. ":" .. status, 1)
-- 请求耗时累计(用于计算平均值)
shared:incr("time:" .. prefix .. ":sum", request_time)
incr("time:" .. prefix .. ":count", 1)
-- 最大耗时
local max_key = "time:" .. prefix .. ":max"
local current_max = shared:get(max_key)
if not current_max or request_time > current_max then
shared:set(max_key, request_time)
end
end
--- 生成指标报告
-- @param ngx_obj nginx 上下文对象
function M.report(ngx_obj)
if not shared then
ngx_obj.status = 500
return ngx_obj.say("metrics not initialized")
end
local lines = {}
-- 遍历共享字典收集所有指标
for key, value in shared:get_keys(0) do
lines[#lines + 1] = key .. " " .. tostring(value)
end
table.sort(lines)
ngx_obj.header("Content-Type", "text/plain; charset=utf-8")
ngx_obj.say("# lolly metrics")
for _, line in ipairs(lines) do
ngx_obj.say(line)
end
end
--- 重置所有指标
-- @param ngx_obj nginx 上下文对象
function M.reset(ngx_obj)
if not shared then
return
end
shared:flush_all()
end
return M