关键在于三步对齐:Nginx输出结构化JSON、Filebeat正确解析提字段、Logstash或ES不破坏原始结构;任一环节出错会导致字段丢失、时间错乱、中文乱码或Kibana中字段未分配。

要让 Nginx 日志顺利进入 ELK 并在 Kibana 中可查、可画图、可筛选,关键不是堆组件,而是三步对齐:Nginx 输出结构化 JSON、Filebeat 正确识别并提字段、Logstash(或 ES)不破坏原始结构。跳过任一环,都会出现字段丢失、时间错乱、中文乱码或 Kibana 里全是 unassigned 字段的问题。
Nginx 配置 JSON 日志格式
默认的 combined 日志是纯文本,靠 Logstash 正则解析,既慢又易错。直接在 Nginx 中定义 JSON 格式,让每条日志本身就是合法 JSON 对象,后续处理压力大幅降低。
- 编辑
/etc/nginx/nginx.conf,在http块内添加自定义 log_format:
- 将 access_log 指向该格式:
access_log /var/log/nginx/access.log json_log; - 执行
nginx -t && nginx -s reload生效 - 用
tail -1 /var/log/nginx/access.log确认输出是单行、无换行、符合 JSON 语法的字符串(注意:不要有尾随逗号、引号要闭合、数字字段不加引号)
Filebeat 正确解析 JSON 字段
Filebeat 默认把整行当字符串塞进 message 字段。要让它“拆开”JSON 并映射为独立字段,必须启用 JSON 解析,并控制字段归属。
- 在
filebeat.inputs下对应 Nginx 日志路径的配置块中,加入:
json.overwrite_keys: true
json.add_error_key: true
-
keys_under_root: true表示把 JSON 内部字段(如status、client_ip)直接提到根层级,而不是嵌套在json.下 -
overwrite_keys: true防止同名字段冲突(比如 Nginx 日志里有status,Filebeat 自身也可能生成status) -
add_error_key: true可捕获解析失败时的错误信息,便于排障 - 确保
paths指向的是上一步配置的 JSON 日志文件路径(如/var/log/nginx/access.log)
Logstash 或直连 ES 的适配要点
如果使用 Logstash 做中间处理,它的配置需与 Filebeat 输出保持一致;如果 Filebeat 直连 Elasticsearch,则要注意索引模板和时间字段。
- 若走 Logstash:Input 插件接收 Filebeat 发来的数据后,无需再做 JSON 解析(因为 Filebeat 已完成),重点放在过滤脏数据、补充地理信息、标准化状态码等业务逻辑
- 若直连 ES:
@timestamp字段必须存在且为 ISO8601 格式(Nginx 的$time_iso8601已满足),否则 Kibana 无法按时间排序或绘图 - 建议在 Filebeat 配置中显式设置时间字段:
processor.timestamp:+event.dataset: nginx.access,方便 Kibana 创建索引模式时自动识别 - 首次启动后,检查 Kibana 的 Stack Management → Index Patterns,确认新索引(如
filebeat-*)已加载,且@timestamp被识别为时间字段
验证与排错提示
常见问题往往出在细节:JSON 格式不合法、Filebeat 权限不足、字段名大小写不一致、Kibana 未刷新索引模式。
- 用
filebeat test output检查是否能连通目标(ES 或 Logstash) - 用
filebeat -e -d "publish"启动调试模式,观察日志是否被读取、字段是否被正确展开 - 在 Kibana 的 Discover 页面,先选对索引模式,再点右上角 Refresh,别忘了点 Auto-refresh 开关
- 如果字段显示为
json.status而非status,说明json.keys_under_root: true没生效或缩进不对 - 中文
user_agent出现乱码,通常因 Nginx 配置中漏了escape=json,导致双引号未转义,JSON 解析中断


















