跳到主要内容

skywalking-logger

skywalking-logger 插件将请求和响应日志作为 JSON 对象以批处理的方式推送到 SkyWalking OAP 服务器,并支持自定义日志格式。

如果存在现有的追踪上下文,它会自动设置追踪日志关联,并依赖于 SkyWalking 跨进程传播头协议

示例

以下示例展示了如何在不同场景下配置 skywalking-logger 插件。

要按照示例操作,请按照 SkyWalking 文档 使用 Docker Compose 启动存储、OAP 和 Booster UI。设置完成后,OAP 服务器应监听 12800,你应该可以通过 http://localhost:8080 访问 UI。

使用默认日志格式记录请求

以下示例展示了如何在路由上配置 skywalking-logger 插件,以记录命中路由的请求信息。

创建一个启用 skywalking-logger 插件的路由,并使用你的 OAP 服务器 URI 配置插件:

curl "http://127.0.0.1:9180/apisix/admin/routes" -X PUT \
-H "X-API-KEY: ${ADMIN_API_KEY}" \
-d '{
"id": "skywalking-logger-route",
"uri": "/anything",
"plugins": {
"skywalking-logger": {
"endpoint_addr": "http://192.168.2.103:12800"
}
},
"upstream": {
"nodes": {
"httpbin.org:80": 1
},
"type": "roundrobin"
}
}'

向路由发送请求:

curl -i "http://127.0.0.1:9080/anything"

你应该会收到一个 HTTP/1.1 200 OK 响应。

SkyWalking UI 中,导航到 General Service > Services。你应该会看到一个名为 APISIX 的服务,其中包含与你的请求对应的日志条目:

{
"upstream_latency": 674,
"request": {
"method": "GET",
"headers": {
"user-agent": "curl/8.6.0",
"host": "127.0.0.1:9080",
"accept": "*/*"
},
"url": "http://127.0.0.1:9080/anything",
"size": 85,
"querystring": {},
"uri": "/anything"
},
"client_ip": "192.168.65.1",
"route_id": "skywalking-logger-route",
"start_time": 1736945107345,
"upstream": "3.210.94.60:80",
"server": {
"version": "3.13.0",
"hostname": "7edbcebe8eb3"
},
"service_id": "",
"response": {
"size": 619,
"status": 200,
"headers": {
"content-type": "application/json",
"date": "Thu, 16 Jan 2025 12:45:08 GMT",
"server": "APISIX/3.13.0",
"access-control-allow-origin": "*",
"connection": "close",
"access-control-allow-credentials": "true",
"content-length": "391"
}
},
"latency": 764.9998664856,
"apisix_latency": 90.999866485596
}

使用插件元数据记录请求和响应头

以下示例展示了如何使用 Plugin Metadata内置变量 自定义日志格式,以记录请求和响应中的特定头部。

在 APISIX 中,Plugin Metadata 用于配置同一插件的所有插件实例的通用元数据字段。当插件在多个资源中启用并且需要对其元数据字段进行通用更新时,这非常有用。

首先,创建一个启用 skywalking-logger 插件的路由,并使用你的 OAP 服务器 URI 配置插件:

curl "http://127.0.0.1:9180/apisix/admin/routes" -X PUT \
-H "X-API-KEY: ${ADMIN_API_KEY}" \
-d '{
"id": "skywalking-logger-route",
"uri": "/anything",
"plugins": {
"skywalking-logger": {
"endpoint_addr": "http://192.168.2.103:12800"
}
},
"upstream": {
"nodes": {
"httpbin.org:80": 1
},
"type": "roundrobin"
}
}'

接下来,配置 skywalking-logger 的插件元数据:

curl "http://127.0.0.1:9180/apisix/admin/plugin_metadata/skywalking-logger" -X PUT \
-H "X-API-KEY: ${ADMIN_API_KEY}" \
-d '{
"log_format": {
"host": "$host",
"@timestamp": "$time_iso8601",
"client_ip": "$remote_addr",
// Annotate 1
"env": "$http_env",
// Annotate 2
"resp_content_type": "$sent_http_Content_Type"
}
}'

❶ 记录自定义请求头 env

❷ 记录响应头 Content-Type

向路由发送带有 env 头的请求:

curl -i "http://127.0.0.1:9080/anything" -H "env: dev"

你应该会收到一个 HTTP/1.1 200 OK 响应。在 SkyWalking UI 中,导航到 General Service > Services。你应该会看到一个名为 APISIX 的服务,其中包含与你的请求对应的日志条目:

[
{
"route_id": "skywalking-logger-route",
"client_ip": "192.168.65.1",
"@timestamp": "2025-01-16T12:51:53+00:00",
"host": "127.0.0.1",
"env": "dev",
"resp_content_type": "application/json"
}
]

有条件地记录请求体

以下示例展示了如何有条件地记录请求体。

创建一个启用 skywalking-logger 插件的路由,如下所示:

curl "http://127.0.0.1:9180/apisix/admin/routes" -X PUT \
-H "X-API-KEY: ${ADMIN_API_KEY}" \
-d '{
"id": "skywalking-logger-route",
"uri": "/anything",
"plugins": {
"skywalking-logger": {
"endpoint_addr": "http://192.168.2.103:12800",
// Annotate 1
"include_req_body": true,
// Annotate 2
"include_req_body_expr": [["arg_log_body", "==", "yes"]]
}
},
"upstream": {
"nodes": {
"httpbin.org:80": 1
},
"type": "roundrobin"
}
}'

include_req_body: 设置为 true 以包含请求体。

include_req_body_expr: 仅当 URL 查询字符串 log_bodyyes 时包含请求体。

向路由发送带有满足条件的 URL 查询字符串的请求:

curl -i "http://127.0.0.1:9080/anything?log_body=yes" -X POST -d '{"env": "dev"}'

你应该会收到一个 HTTP/1.1 200 OK 响应。在 SkyWalking UI 中,导航到 General Service > Services。你应该会看到一个名为 APISIX 的服务,其中包含与你的请求对应的日志条目,并且记录了请求体:

[
{
"request": {
"url": "http://127.0.0.1:9080/anything?log_body=yes",
"querystring": {
"log_body": "yes"
},
"uri": "/anything?log_body=yes",
...,
"body": "{\"env\": \"dev\"}",
},
...
}
]

向路由发送不带任何 URL 查询字符串的请求:

curl -i "http://127.0.0.1:9080/anything" -X POST -d '{"env": "dev"}'

你不应该观察到没有请求体的日志条目。

信息

除了将 include_req_bodyinclude_resp_body 设置为 true 之外,如果你自定义了 log_format,插件将不会在日志中包含 body。

作为一种解决方法,你也许能够在日志格式中使用 NGINX 变量 $request_body,例如:

{
"skywalking-logger": {
...,
"log_format": {"body": "$request_body"}
}
}

将追踪与日志关联

以下示例展示了如何在路由上配置 skywalking-logger 插件,以记录命中路由的请求信息。

创建一个启用 skywalking-logger 插件的路由,并使用你的 OAP 服务器 URI 配置插件:

curl "http://127.0.0.1:9180/apisix/admin/routes" -X PUT \
-H "X-API-KEY: ${ADMIN_API_KEY}" \
-d '{
"id": "skywalking-logger-route",
"uri": "/anything",
"plugins": {
"skywalking": {
"sample_ratio": 1
},
"skywalking-logger": {
"endpoint_addr": "http://192.168.2.103:12800"
}
},
"upstream": {
"nodes": {
"httpbin.org:80": 1
},
"type": "roundrobin"
}
}'

向路由生成一些请求:

curl -i "http://127.0.0.1:9080/anything"

你应该会收到 HTTP/1.1 200 OK 响应。

SkyWalking UI 中,导航到 General Service > Services。你应该会看到一个名为 APISIX 的服务,其中包含与你的请求对应的追踪,你可以在其中查看关联的日志:

trace context

associated log