nginx 将 $request_body 记录为十六进制

问题描述 投票:0回答:5

我正在尝试将请求的请求正文记录到我的 api,并且 nginx 正在将所有引号(以及一些其他字符,如空格和制表符)转换为十六进制字符。

这是我的日志格式

log_format postdata '{"ts": "$time_iso8601", "status": $status, "req": "$uri", "meth": "$request_method", "body": "$request_body"}';

这是记录的内容

{"ts": "2015-05-20T15:31:11-07:00", "status": 400, "req": "/v2/track", "meth": "POST", "body": {\x22id\x22:\x22user id\x22}}

如何防止这种情况发生,以便生成的日志行是

{"ts": "2015-05-20T15:31:11-07:00", "status": 400, "req": "/v2/track", "meth": "POST", "body": {"id":"user id"}}
json nginx hex
5个回答
28
投票

自 1.13 起,有一个“escape=none”参数可以关闭数据转义。

http://nginx.org/en/docs/http/ngx_http_log_module.html#log_format

log_format  api_request_log escape=none '[$time_local] $request \n$request_body';

9
投票

你无法阻止它,并且必须对其进行后期处理。

Python2示例:

line = '{\x22id\x22:\x22user id\x22}'
line.decode('unicode_escape')
>> u'{"id":"user id"}'

Python3示例:

line = '{\x22id\x22:\x22user id\x22}'
bytes(line, 'utf-8').decode('unicode_escape')
>> '{"id":"user id"}'

Ruby 示例(来自 https://stackoverflow.com/a/18752208/2398354):

require 'yaml'
line = '{\x22id\x22:\x22user id\x22}'
YAML.load(%Q(---\n"#{line}"\n))
=> "{\"id\":\"user id\"}"

注意:如果使用 Logstash 对文件进行后处理,最后一个示例非常有用


9
投票

希望这对某人有帮助。 为了记录整个 json 请求而不进行转义。 请在 http 块中添加此配置

http {
 log_format postdata escape=json $request_body;
 access_log /var/log/nginx/access.log postdata;
 .....
}

0
投票

正如其他人所说,无法在 nginx 配置中修复此问题。 但后期处理并不困难。如果请求正文是 JSON 格式,您可能会遇到很多 \x0A(换行符)和 \x22(“)。

在查看日志文件之前只需使用

sed
清除这些内容即可。

这是给您的命令:

LANG='' sed -E 's/(\\x0A|\\x22)//g' access.log


0
投票

你可以在 bash\zsh 中完成:

echo -e '{\x22id\x22:\x22user id\x22}'
{"id":"user id"}
© www.soinside.com 2019 - 2024. All rights reserved.