Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(promethues): add ngx.shared.DICT status #7412

Merged
merged 20 commits into from
Jul 19, 2022
Merged
Show file tree
Hide file tree
Changes from 10 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
44 changes: 44 additions & 0 deletions apisix/plugins/prometheus/exporter.lua
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ local get_services = require("apisix.http.service").services
local get_consumers = require("apisix.consumer").consumers
local get_upstreams = require("apisix.upstream").upstreams
local clear_tab = core.table.clear
local concat_tab = core.table.concat
local get_stream_routes = router.stream_routes
local get_protos = require("apisix.plugins.grpc-transcode.proto").protos
local service_fetch = require("apisix.http.service").get
Expand Down Expand Up @@ -122,6 +123,10 @@ function _M.http_init(prometheus_enabled_in_stream)
"Etcd modify index for APISIX keys",
{"key"})

metrics.shared_dict = prometheus:gauge("shared_dict",
"nginx shared DICT of APISIX",
{"key"})
ccxhwmy marked this conversation as resolved.
Show resolved Hide resolved

-- per service

-- The consumer label indicates the name of consumer corresponds to the
Expand Down Expand Up @@ -351,6 +356,42 @@ local function etcd_modify_index()

end

local key = {}
local combine_param = {}
tzssangglass marked this conversation as resolved.
Show resolved Hide resolved

local function shared_dict_status()
local header_of_shared_dict = core.request.header(ngx.ctx, "shared_dict")
ccxhwmy marked this conversation as resolved.
Show resolved Hide resolved
if not header_of_shared_dict then
ccxhwmy marked this conversation as resolved.
Show resolved Hide resolved
return
end

local set_shared_dict_param = function (shared_dict_name)
ccxhwmy marked this conversation as resolved.
Show resolved Hide resolved
if type(shared_dict_name) ~= "string" then
return
end
local share_dict = ngx.shared[shared_dict_name]
if share_dict then
combine_param[1] = shared_dict_name
combine_param[2] = "capacity"
key[1] = concat_tab(combine_param, "_")
metrics.shared_dict:set(share_dict:capacity(), key)

combine_param[2] = "free_space"
key[1] = concat_tab(combine_param, "_")
metrics.shared_dict:set(share_dict:free_space(), key)
end
end
tzssangglass marked this conversation as resolved.
Show resolved Hide resolved

if type(header_of_shared_dict) == "string" then
set_shared_dict_param(header_of_shared_dict)
end

if type(header_of_shared_dict) == "table" then
for _, shared_dict_name in ipairs(header_of_shared_dict) do
set_shared_dict_param(shared_dict_name)
end
end
end

local function collect(ctx, stream_only)
if not prometheus or not metrics then
Expand All @@ -359,6 +400,9 @@ local function collect(ctx, stream_only)
return 500, {message = "An unexpected error occurred"}
end

-- collect ngx.shared.DICT status
shared_dict_status()

-- across all services
nginx_status()

Expand Down
5 changes: 5 additions & 0 deletions docs/en/latest/plugins/prometheus.md
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,7 @@ The following metrics are exported by the `prometheus` Plugin:
| node | IP address of the Upstream node. |

- Info: Information about the APISIX node.
- Shared dict: capacity and free space of ngx.shared.DICT, this param uses the request header `Shared_DICT` to carry the shared memory name to be fetched.

Here are the original metrics from APISIX:

Expand Down Expand Up @@ -272,6 +273,10 @@ apisix_http_latency_bucket{type="upstream",route="1",service="",consumer="",node
# HELP apisix_node_info Info of APISIX node
# TYPE apisix_node_info gauge
apisix_node_info{hostname="desktop-2022q8f-wsl"} 1
# HELP apisix_shared_dict nginx shared DICT of APISIX
# TYPE apisix_shared_dict gauge
apisix_shared_dict{key="internal-status_capacity"} 10485760
apisix_shared_dict{key="internal-status_free_space"} 10407936
```

## Disable Plugin
Expand Down
9 changes: 7 additions & 2 deletions docs/zh/latest/plugins/prometheus.md
Original file line number Diff line number Diff line change
Expand Up @@ -198,14 +198,15 @@ scrape_configs:
| node | 上游节点的 IP 地址。 |

- Info: 当前 APISIX 节点信息。
- Shared dict: 共享内存的大小以及剩余可用空间,该指标使用请求头 `Shared_DICT` 携带需要查询的共享内存名称。

以下是 APISIX 的原始的指标数据集:

```shell
curl http://127.0.0.1:9091/apisix/prometheus/metrics
curl http://127.0.0.1:9091/apisix/prometheus/metrics -H "Shared_DICT:internal-status"
```

```
```shell
# HELP apisix_bandwidth Total bandwidth in bytes consumed per service in Apisix
# TYPE apisix_bandwidth counter
apisix_bandwidth{type="egress",route="",service="",consumer="",node=""} 8417
Expand Down Expand Up @@ -269,6 +270,10 @@ apisix_http_latency_bucket{type="upstream",route="1",service="",consumer="",node
# HELP apisix_node_info Info of APISIX node
# TYPE apisix_node_info gauge
apisix_node_info{hostname="APISIX"} 1
# HELP apisix_shared_dict nginx shared DICT of APISIX
# TYPE apisix_shared_dict gauge
apisix_shared_dict{key="internal-status_capacity"} 10485760
apisix_shared_dict{key="internal-status_free_space"} 10407936
```

## 禁用插件
Expand Down
36 changes: 36 additions & 0 deletions t/plugin/prometheus.t
Original file line number Diff line number Diff line change
Expand Up @@ -632,3 +632,39 @@ GET /apisix/prometheus/metrics
qr/apisix_/
--- response_body_unlike eval
qr/etcd/



=== TEST 42: fetch the prometheus one shared dict data
--- request
GET /apisix/prometheus/metrics
--- more_headers
Shared_DICT: worker-events
--- response_body_like
.*TYPE apisix_shared_dict gauge.*worker-events_capacity.*worker-events_free_space.*



=== TEST 43: fetch the prometheus multiple shared dict data
--- request eval
["GET /apisix/prometheus/metrics", "GET /apisix/prometheus/metrics", "GET /apisix/prometheus/metrics"]
--- more_headers
Shared_DICT: worker-events
Shared_DICT: upstream-healthcheck
Shared_DICT: internal-status
--- response_body_like eval
[".*TYPE apisix_shared_dict gauge.*upstream-healthcheck_capacity.*upstream-healthcheck_free_space.*",
".*TYPE apisix_shared_dict gauge.*internal-status_capacity.*internal-status_free_space.*",
".*TYPE apisix_shared_dict gauge.*worker-events_capacity.*worker-events_free_space.*"]



=== TEST 44: fetch the prometheus multiple shared dict data contain not exist shared dict
--- request
GET /apisix/prometheus/metrics
--- more_headers
Shared_DICT: worker-events
Shared_DICT: upstream-healthcheck
Shared_DICT: not-exist-shared-dict
--- response_body_unlike
.*TYPE apisix_shared_dict gauge.*not-exist-shared-dict_capacity.*not-exist-shared-dict_free_space.*