在运维项目的时候,一旦出了什么问题就非常的头痛,无论是查找日志还是分析日志错误,都是令人烦躁的。
告别传统的服务器日志打捞和日志分析,搭建自动化日志收集、分析工具ELK。
elasticsearch
Elasticsearch 是一个分布式、RESTful 风格的搜索和数据分析引擎,能够解决不断涌现出的各种用例。作为 Elastic Stack 的核心,Elasticsearch 会集中存储您的数据,让您飞快完成搜索,微调相关性,进行强大的分析,并轻松缩放规模。
Elasticsearch:官方分布式搜索和分析引擎 | Elastic
Docker安装elasticsearch
docker-compose.yml
version: '3'
services:
elasticsearch:
image: elasticsearch:7.14.2 #镜像
container_name: elasticsearch #定义容器名称
restart: always #开机启动,失败也会一直重启
environment:
- "cluster.name=elasticsearch" #设置集群名称为elasticsearch
- "discovery.type=single-node" #以单一节点模式启动
- "ES_JAVA_OPTS=-Xms512m -Xmx1024m" #设置使用jvm内存大小
volumes:
- ./plugins:/usr/share/elasticsearch/plugins #插件文件挂载
- es_data:/usr/share/elasticsearch/data #数据文件挂载
- docker.elastic.co/elasticsearch/elasticsearch:7.14.2 #数据文件挂载
ports:
- 9200:9200
在当前yml文件夹使用docker-compose命令启动es,访问ip:9200,看到输出json即可
logstash
Logstash 是免费且开放的服务器端数据处理管道,能够从多个来源采集数据,转换数据,然后将数据发送到您最喜欢的“存储库”中。
Docker安装logstash
mkdir /home/mycontainers/logstash/config
mkdir /home/mycontainers/logstash/pipeline
以上来个文件用于挂载logstash文件
然后在config文件夹里面新建以下文件
touch logstash.yml
vi logstash.yml
logstash.yml输入以下内容
xpack.monitoring.elasticsearch.hosts: [ "http://elasticsearch:9200" ]
然后切换到pipeline文件夹
新建配置文件
touch my.conf
vi my.conf
input {
tcp {
port => 5044
}
}
filter {
date {
match => ["content","yyyy-MM-dd_HH-mm-ss"]
target => "content"
}
}
output {
elasticsearch {
hosts => ["http://elasticsearch:9200"]
index => "mylog"
}
}
mylogstash.yml
version: '3'
services:
logstash:
container_name: logstash
network_mode: mynetwork
image: docker.elastic.co/logstash/logstash:7.12.0 # 替换为所需的 Logstash 版本
volumes:
- /home/mycontainers/logstash/config:/usr/share/logstash/config # 挂载 Logstash 配置文件
- /home/mycontainers/logstash/pipeline:/usr/share/logstash/pipeline # 挂载 Logstash Pipeline 配置文件
ports:
- 5044:5044 # 映射 Logstash 输入端口
然后使用docker-compose命令启动即可
如果启动过程中遇到问题,可以尝试不使用docker-compose启动,使用docker命令启动,然后把容器里面的config文件夹和pipeline文件夹copy到宿主机中,然后再使用docker-compose进行挂载启动。
如果遇到jvm问题,打开jvm.options文件把以下配置注释掉
# 8-13:-XX:+UseConcMarkSweepGC
kibana
使用 Kibana 针对大规模数据快速运行数据分析,以实现可观测性、安全和搜索。对来自任何来源的任何数据进行全面透彻的分析,从威胁情报到搜索分析,从日志到应用程序监测,不一而足。
Docker安装kibana
docker-compose.yml
version: '3'
services:
kibana:
image: kibana:7.14.2
network_mode: mynetwork
container_name: kibana
restart: always
volumes:
- ./kibana.yml:/usr/share/kibana/config/kibana.yml
ports:
- 5601:5601
privileged: true #环境变量
kibana.yml
server.name: kibana
# kibana的主机地址 0.0.0.0可表示监听所有IP
server.host: "0.0.0.0"
#
# 这边设置自己es的地址,
elasticsearch.hosts: http://elasticsearch:9200
elasticsearch.username: 'kibana'
elasticsearch.password: '123456'
# # 显示登陆页面
xpack.monitoring.ui.container.elasticsearch.enabled: true
# 开启中文模式
i18n.locale: "zh-CN"
执行docker-compose命令启动,控制台不报错即可。访问ip:5601,看到kibana首页即证明成功启动
Spring Boot
日志配置
logging:
file:
path: ./logs/mylog-${server.port}.logs
logback-spring.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<!-- 引入SpringBoot的默认配置文件defaults.xml -->
<include resource="org/springframework/boot/logging/logback/defaults.xml"/>
<!-- <property name="LOG_FILE" value="${LOG_FILE:-${LOG_PATH:-${LOG_TEMP:-${java.io.tmpdir:-/tmp}}}/spring.log}"/>-->
<!-- 引入SpringBoot中内置的控制台输出配置文件console-appender.xml -->
<include resource="org/springframework/boot/logging/logback/console-appender.xml"/>
<!-- 引入自定义的文件输出配置文件logback-spring-file-level.xml -->
<include resource="logback-spring-file-level.xml"/>
<!-- 设置root logger的级别为INFO,并将控制台输出和文件输出中的appender都添加到root logger下 -->
<root level="INFO">
<appender-ref ref="CONSOLE"/>
<appender-ref ref="WARN_FILE"/>
<appender-ref ref="ERROR_FILE"/>
<appender-ref ref="LOGSTASH"/>
</root>
<!-- jmx可以动态管理logback配置-->
<jmxConfigurator/>
</configuration>
如果想保留控制台输出日志,请保留<appender-ref ref="CONSOLE"/>
,如果不想保留就注释掉
logback-spring-file-level.xml
<?xml version="1.0" encoding="UTF-8"?>
<included>
<!--只保留 WARN Level的日志-->
<appender name="WARN_FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
<rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
<!-- %i用来标记分割日志的序号 -->
<fileNamePattern>${LOG_FILE}.WARNLevel.%d{yyyy-MM-dd}.%i.log</fileNamePattern>
<!-- 单个日志文件最大10MB, 保存3天的历史日志, 所有日志文件最大50MB -->
<maxFileSize>10MB</maxFileSize>
<maxHistory>3</maxHistory>
<totalSizeCap>50MB</totalSizeCap>
</rollingPolicy>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>WARN</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
<encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
<!-- <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} %X{request_id} - %msg%n</pattern>-->
<pattern>%d{"yyyy-MM-dd HH:mm:ss.SSS"} %-5level [%logger - %M] - %msg%n</pattern>
</encoder>
</appender>
<!--保留ERROR Level的日志-->
<appender name="ERROR_FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
<rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
<!-- %i用来标记分割日志的序号 -->
<fileNamePattern>${LOG_FILE}.ERRORLevel.%d{yyyy-MM-dd}.%i.log</fileNamePattern>
<!-- 单个日志文件最大10MB, 保存3天的历史日志, 所有日志文件最大50MB -->
<maxHistory>3</maxHistory>
<maxFileSize>10MB</maxFileSize>
<totalSizeCap>50MB</totalSizeCap>
<!-- <cleanHistoryOnStart>true</cleanHistoryOnStart>-->
</rollingPolicy>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<level>ERROR</level>
<onMatch>ACCEPT</onMatch>
<onMismatch>DENY</onMismatch>
</filter>
<encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
<pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} %X{request_id} - %msg%n</pattern>
</encoder>
</appender>
<!-- 这向logstash发送并且收集信息 -->
<appender name="LOGSTASH" class="net.logstash.logback.appender.LogstashTcpSocketAppender">
<destination>你的ip:5044</destination>
<encoder charset="UTF-8" class="net.logstash.logback.encoder.LogstashEncoder" />
</appender>
</included>
测试接口
@GetMapping("/checkLog")
public String checkToken111() {
log.error("出错了");
return userService.sayHello();
}
测试
启动项目后就能在kibana看到mylog索引了,创建索引模式后,可以在可视化界面看到相关日志信息,如下图
里面都是项目启动的info信息
然后我们测试一下接口,看一下error是否顺利收集
ApiFox发送请求
kibana可视化
可以看到,error日志也是可以收集到了
kibana开发工具
进入kibana开发工具,使用控制台进行数据查询
GET mylog/_search
{
"fields": [
"message"
],
"query": {
"match": {
"message": "出错了"
}
}
}
具体查询语法请看
搜索接口 |弹性搜索指南 [7.14] |弹性的 (elastic.co)
总结
难点
难点总体来说就是配置日志文件比较麻烦,按照以上配置进行配置,改一下对应端口应该不会有什么问题。
还有一点就是logstash,初次搞logstash的话可能会比较麻烦,毕竟是第一次,笔者也是踩了很多坑。遇到不懂的问题可以去问一下GPT或者根据控制台反应的信息进行排查和搜索资料。
如有什么疑点和建议,评论区留言,我也会这两天深入学习一下ELK,进行一个拓展或者补充。