Yan.G WebServer Dev Engineer

ELK Nginx 日志 监控

2020-05-03

ELk 搭建记录

Nginx 日志监控,需要对请求日志进行详细的数据采集,为公司提供数据支持,可以作为采集加记录的一个代表

接上一篇幅 elk-php

我们已经通过fileBeat 将日志发送给 logStash, 这一片主要介绍如何拆解日志 Nginx 的错误日志为普通的文本记录,和php的记录方式大同小异,不在记录

  • 以下我们Nginx 的 access_log 格式 ```bash user nginx; worker_processes 1; pid /var/run/nginx.pid;

events { worker_connections 1024; }

http { include /etc/nginx/mime.types; default_type application/octet-stream; # $request_id 是为了查问题方便的一个请求唯一值,通过这个值,我们可以查出来一个请求的完整路线, # 在 /etc/nginx/fastcgi_params 追加 fastcgi_param HTTP_REQUEST_ID $request_id; 即可 (不同的 cgi 不同的配置中加)

log_format  main  escape=json '$request_id $remote_addr - $remote_user [$time_local] $host "$request" '
                  '"$request_body" $status $body_bytes_sent "$http_referer" '
                  '"$http_user_agent" $upstream_addr $request_time $upstream_response_time';

sendfile        on;
keepalive_timeout  65;

gzip on;
gzip_static on;
gzip_comp_level 4;
gzip_types application/json text/css application/javascript;

include /etc/nginx/conf.d/*.conf; } ```
  • 日志格式我们记录为 json,搜集后的的数据格式如下
    515e3edd2070c42d12bf66f12de69997 125.35.107.22 -  [25/May/2020:17:17:28 +0800] d.test.com "POST /api/v1/test/log HTTP/1.1" "{\"log\":[{\"action\":\"class\",\"time\":1}],\"start_time\":1590398253}" 200 95 "" "okhttp/4.0.0" 172.18.0.4:9000 0.167 0.167
    

编写解析文件

cat /opt/elk/logstash-6.4.2/input/stage_nginx_access.conf

input{
        beats {
            port => 5044
        }
}

filter {
    if [tags][0] == "stage-nginx-access" {
               grok {
                   match => {
                       "message" => "%{DATA:request_id} %{IPV4:remote_addr} - (%{DATA:remote_user}|-) \[%{HTTPDATE:request_time}\] (%{HOSTNAME:http_host}) \"%{WORD:verb} %{URIPATHPARAM:request} HTTP/%{NUMBER:httpversion}\" \"%{DATA:request_body}\" %{NUMBER:status} %{NUMBER:bytes} \"%{DATA:refer}\" \"(%{DATA:user_agent}|-)\" %{NOTSPACE:upstream_addr} (%{BASE16FLOAT:reqeust_time}|-) (%{BASE16FLOAT:upstream_response_time}|-)"
                   }
                   remove_field => ["message"]
               }
               geoip {
                   source => "remote_addr"
                   target => "geoip"
                   database => "/opt/elk/GeoLite2-City_20181016/GeoLite2-City.mmdb"
                   add_field => [ "[geoip][coordinates]", "%{[geoip][longitude]}" ]
                   add_field => [ "[geoip][coordinates]", "%{[geoip][latitude]}" ]
               }
               mutate {
                   convert => [ "[geoip][coordinates]", "float" ]
                   convert => [ "response","integer" ]
                   convert => [ "bytes","integer" ]
                   gsub    => [ "request","\/\d+","/id" ]
               }
               date {
                   locale => "en_US"
                   match => ["request_time", "dd/MMM/yyyy:HH:mm:ss Z"]
                   target => "@timestamp"
               }
    }
}

output {
    if [tags][0] == "stage-nginx-access" {
               elasticsearch {
                   hosts => "127.0.0.1:9200"
                   action => "index"
                   index => "logstash-stage-nginx-access"
               }
               stdout { codec => rubydebug }
    }
}

filter 插件

  • 通过 fileBeat 的type 来区分不同的输入端,确认不同的解析脚本
  • grok 可以匹配日志文件的具体字段,通过http://grokdebug.herokuapp.com/ 可以在线检测是否正确
  • geoIp 可以通过服务端IP匹配具体的城市,将数据可视化,直接采用 GEO数据即可
  • mutate 为数据加工,支持正则 例如将 /good/1 更改为 /good/id
gsub    => [ "request","good\/\dd+","good/id" ]

Similar Posts

下一篇 GO 学习笔记

Content