背景

客户使用nginx做前端负载均衡转发,承载对象存储的业务。对象存储的qps较大, 基本每天在500万左右的请求。单个请求的失败或者处理异常很难从日志里面去定位(每天日志量大概在300G左右)。这个时候,引入入ELK进行日志分析最适合不过了。

本文模拟真实的请求日志,搭建一个ELK进行nginx分析的demo系统。

部署架构

因为是demo环境,目前部署架构如下:

nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_nginx

  1. Elasticsearch一共3个节点
  2. Kibana、Nginx、Logstash同机部署
  3. kibana通过Nginx对外暴露服务
  4. Logstash将Nginx的access log写入到Elasticsearch中

机器配置

机器角色

配置

操作系统

Nginx/Kibana/Logstah

2核4G

Centos 7.6

Elasticsearch

2核4G 50G数据盘

Centos 7.6

ES/Lostash/Kibana的版本:7.9.1

部署步骤

ELK部署

  • 部署java 环境 需要设置JAVA_HOME变量
  • 配置可用的ELK yum源

nginx的安装

前面elk的安装参考其他人写的就行。这里介绍一下nginx的安装,因为要用到nginx的一共特性(标识request的request id, 这个在nginx 1.11以后才有),需要安装最新的nginx。

  • 卸载原有nginxyum remove nginx
  • 下载最新的nginx epelwget http://nginx.org/packages/centos/7/noarch/RPMS/nginx-release-centos-7-0.el7.ngx.noarch.rpm
  • 安装rpm -ivh nginx-release-centos-7-0.el7.ngx.noarch.rpm
  • 安装nginxyum install nginx

配置软件

Elasticsearch配置

默认采用yum安装的,配置文件在/etc/elasticsearch/目录下。主要的配置文件为:

  • elasticsearch.yml 服务主要配置文件
  • jvm.options jvm配置

elasticsearch.yml主要定义了端口,节点,日志等信息,里面配置较多。这里列出当前测试下的配置。

# cat elasticsearch.yml |grep -v "^#" |grep -v "^$"

如上的数据目录需要提前配置好,并且修改owner为elasticsearch·

mkdir -p /data/els_data
mkdir -p /var/log/elasticsearch
chown -R elasticsearch.elasticsearch /data/els_data
chown -R elasticsearch.elasticsearch /var/log/elasticsearch

jvm.options的主要配置,主要是如下两个,限制内存的。这个配置建议不超过机器的一半。这里我是测试,就直接用512M了。

# Xms represents the initial size of total heap space
  • 启动停止和开机启动 通过yum安装之后在centos可以直接使用systemctl进行操作。三个节点,依次启动即可。
#启动

启动完成之后,可以看到端口监听如下,其中9200是对外服务端口,9300是集群内部通信用端口

tcp6       0      0 172.16.0.46:9200        :::*                    LISTEN      1827691/java        
tcp6       0      0 172.16.0.46:9300        :::*                    LISTEN      1827691/java

三个节点都启动之后,可以通过如下接口检查es集群的状态

# curl 172.16.0.46:9200/_cluster/health?pretty

主要关注status和副本数情况。

1. status 为green 是正常的。

2. 副本数active_shards是active_primary_shards的2倍。另外unassigned_shards为0

kibana配置

使用yum安装,配置文件在/etc/kibana/下,主要配置文件为kibana.yml, 这里主要看一下自定义的配置以及解释,其他配置保持默认即可

# cat kibana.yml| grep -v "^#"| grep -v "^$"
  • 服务启动停止 同样使用systemctl操作即可
# 启动

kibana启动成功之后,可以看到5601端口在监听。

tcp        0      0 0.0.0.0:5601            0.0.0.0:*               LISTEN      4315/node

nginx 配置

  • 配置日志格式 在/etc/nginx/nginx.conf的http下添加如下配置,将日志打为json格式,还原真实业务场景
'{"@timestamp":"$time_iso8601",'
  • 代理kibana 在/etc/nginx/conf.g/添加elk.conf,内容如下:
# cat elk.conf
  • 启动和停止 同样使用systemctl来进行服务启动停止
systemctl start nginx
systemctl stop nginx
systemctl status nginx

启动完成之后,可以通过浏览器访问这页面,会跳转到kibana的页面了。这里我是通过本地8000隧道转发到机器的80端口了。

nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_nginx_02

所以我用本地8000端口打开的页面。

nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_配置文件_03

logstash的配置

默认通过yum安装之后,配置文件在/etc/logstash下

# tree

logstash.yml保持默认即可。这里主要看conf.d下的nginx.conf

# cat conf.d/nginx.conf

input部分定义了什么样的文件写入到es,output定义了写到哪个es去。

这里可以对日志进行各种处理,如拆分,聚合等,详细可以参考logstash的配置。

不过我们的demo环境已经把nginx的日志格式化为json了,这里直接导入es即可。

  • 验证配置文件是否正确
cd /usr/share/logstash/bin
  • 启动和停止
systemctl start logstash
systemctl stop logstash

启动之后,可以看配置文件中的日志文件,观察是否写入es成功。 

如果不能写入,查看一下logstash的日志,可能原因access log的权限不对,不能写入。因为access log是nginx进程在管理,可能使用nginx用户。而logstash是由logstash用户启动,手动修改access的权限即可。

写入成功之后,可以在es上通过接口查看索引的情况

# curl 172.16.0.39:9200/_cat/indices?v

部署完成之后,在kibana上建立索引模式之后,就可以在kibana上查看nginx的请求



nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_nginx_04



可以查看整体请求的情况

nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_nginx_05

另外可以根据请求id,来查看具体请求的情况(这里是模拟业务的场景,根据反馈给客户端的请求id,判断请求的具体情况,远程ip,报错信息等。)

nginx 代理post请求 转发为get 并携带参数 nginx 转发所有请求_nginx_06