安装ELK
本文采用docker-compose安装docker-elk,请先安装docker及docker-compose内容
docker-elk源码:https://github.com/deviantony/docker-elk
克隆源码地址 :git clone https://github.com/deviantony/docker-elk
修改.env文件,更改成自己的密码
启动
docker compose up setup
docker compose up -d
访问:http://localhost:5601 账号ekastic 密码为.env修密码
调整logstash
配置多端口形式
在docker-elk当前目录编辑docker-compose.yml配置文件
找到logstash的配置,如下:
修改为端口段的形式
services:
logstash:
port:
# 增加端口
- "50000-50010:50000-50010/tcp"
- "50000-50010:50000-50010/udp"
增加索引权限
编辑vim setup/roles/logstash_writer.json
{ "cluster": [ "manage_index_templates", "monitor", "manage_ilm" ], "indices": [ { "names": [ "logs-generic-default", "logstash-*", "ecs-logstash-*", "springboot-*" // 自定义索引前缀 ], "privileges": [ "write", "create", "create_index", "manage", "manage_ilm" ] }, { "names": [ "logstash", "ecs-logstash" ], "privileges": [ "write", "manage" ] } ] }
修改logstash配置
├── logstash
│ ├── config
│ │ └── logstash.yml
│ ├── Dockerfile
│ └── pipeline
│ └── logstash.conf
在 logstash/pipline/logstash.conf 进行配置(如需要接入多个不同的应用日志收集则配置不同的端口进行区分)
input { beats { port => 5044 type => 'beats' } tcp { port => 50000 type => 'test1' } tcp { port => 50001 type => 'test2' } } ## Add your filters / logstash plugins configuration here output { if [type] == 'beats' { elasticsearch { hosts => "elasticsearch:9200" user => "logstash_internal" password => "${LOGSTASH_INTERNAL_PASSWORD}" } } else if [type] == 'test1' { elasticsearch { hosts => "elasticsearch:9200" user => "logstash_internal" password => "${LOGSTASH_INTERNAL_PASSWORD}" index => "springboot-test1%{+YYYY.MM}" } } else if [type] == 'test2' { elasticsearch { hosts => "elasticsearch:9200" user => "logstash_internal" password => "${LOGSTASH_INTERNAL_PASSWORD}" index => "springboot-test2%{+YYYY.MM}" } } }
以上内容修改完成后重启下elk
docker compose up setup
docker compose down
docker compose up -d
Springboot接入ELK
使用的是log4j2, 在resources下创建对象 log4j2-spring.xml
其中 host 就是主机的ip,port是50000 具体可以在docker-elk 中的 logstash/pipeline/logstash.conf 中配置
采用异步的方式
<Appenders>
<Socket name="Logstash" host="127.0.0.1" port="50000" protocol="TCP">
<JsonLayout compact="true" eventEol="true">
<!-- 可读时间 -->
<KeyValuePair key="timestamp" value="%d{yyyy-MM-dd HH:mm:ss.SSS}"/>
</JsonLayout>
</Socket>
<Async name="LogstashAsync">
<AppenderRef ref="Logstash"/>
</Async>
</Appenders>
<loggers>
<Root level="info">
<Appender-ref ref="LogstashAsync" /> <!--ELK-->
</Root>
</loggers>
完整配置参考
<?xml version="1.0" encoding="UTF-8"?>
<!--Configuration后面的status,这个用于设置log4j2自身内部的信息输出,可以不设置,当设置成trace时,你会看到log4j2内部各种详细输出-->
<!--monitorInterval:Log4j能够自动检测修改配置 文件和重新配置本身,设置间隔秒数-->
<configuration monitorInterval="5">
<!--日志级别以及优先级排序: OFF > FATAL > ERROR > WARN > INFO > DEBUG > TRACE > ALL -->
<!--变量配置-->
<Properties>
<Property name="LOG_EXCEPTION_CONVERSION_WORD">%xwEx</Property>
<Property name="LOG_LEVEL_PATTERN">%5p</Property>
<Property name="LOG_DATEFORMAT_PATTERN">yyyy-MM-dd HH:mm:ss.SSS</Property>
<!-- 定义日志存储的路径 -->
<Property name="FILE_LOG_BASE_PATH">./system-log</Property>
<Property name="APPLICATION_NAME">${spring.application.name}</Property>
<!-- 控制台的日志格式 -->
<Property name="CONSOLE_LOG_PATTERN">%clr{%d{${sys:LOG_DATEFORMAT_PATTERN}}}{faint} %clr{${sys:LOG_LEVEL_PATTERN}} %clr{%pid}{magenta} %clr{---}{faint} %clr{[%15.15t]}{faint} %clr{%-40.40c{1.}}{cyan} %clr{:}{faint} %m%n${sys:LOG_EXCEPTION_CONVERSION_WORD}</Property>
<!-- 日志文件的日志格式 -->
<Property name="FILE_LOG_PATTERN">%d{${sys:LOG_DATEFORMAT_PATTERN}} ${sys:LOG_LEVEL_PATTERN} %pid --- [%t] %-40.40c{1.} : %m%n${sys:LOG_EXCEPTION_CONVERSION_WORD}</Property>
<!-- 格式化输出:%date表示日期,%thread表示线程名,%-5level:级别从左显示5个字符宽度 %msg:日志消息,%n是换行符-->
</Properties>
<Appenders>
<Console name="Console" target="SYSTEM_OUT" follow="true">
<!--输出日志的格式-->
<PatternLayout pattern="${sys:CONSOLE_LOG_PATTERN}" charset="${sys:CONSOLE_LOG_CHARSET}"/>
<!--控制台只输出level及其以上级别的信息(onMatch),其他的直接拒绝(onMismatch)-->
<!-- <ThresholdFilter level="info" onMatch="ACCEPT" onMismatch="DENY"/> -->
</Console>
<!-- ELK 日志配置-->
<Socket name="Logstash" host="127.0.0.1" port="50000" protocol="TCP">
<JsonLayout compact="true" eventEol="true">
<!-- 可读时间 -->
<KeyValuePair key="timestamp" value="%d{yyyy-MM-dd HH:mm:ss.SSS}"/>
</JsonLayout>
</Socket>
<Async name="LogstashAsync">
<AppenderRef ref="Logstash"/>
</Async>
<!-- 这个会打印出所有的info及以下级别的信息,每次大小超过size,则这size大小的日志会自动存入按年份-月份建立的文件夹下面并进行压缩,作为存档-->
<RollingFile name="RollingFileInfo" fileName="${FILE_LOG_BASE_PATH}/info.log" filePattern="${FILE_LOG_BASE_PATH}/INFO-%d{yyyy-MM-dd}_%i.log.gz">
<!--控制台只输出level及以上级别的信息(onMatch),其他的直接拒绝(onMismatch)-->
<ThresholdFilter level="info" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout pattern="${FILE_LOG_PATTERN}"/>
<Policies>
<!--超过100M增加序号-->
<SizeBasedTriggeringPolicy size="10MB"/>
<!-- 每天滚动 -->
<TimeBasedTriggeringPolicy interval="1" modulate="true"/>
</Policies>
<DefaultRolloverStrategy>
<!-- 关键点:按时间删除旧文件(优先级高于max序号) -->
<Delete basePath="${FILE_LOG_BASE_PATH}" maxDepth="1">
<IfFileName regex="INFO-\d{4}-\d{2}-\d{2}_\d+\.log\.gz" /> <!-- 匹配压缩日志 -->
<IfLastModified age="180d" /> <!-- 180天前的文件 -->
</Delete>
<!-- 控制最大序号数(次要限制) -->
<Max>10</Max> <!-- 每个日期最多保留10个序号文件 -->
</DefaultRolloverStrategy>
</RollingFile>
<!-- 这个会打印出所有的warn及以下级别的信息,每次大小超过size,则这size大小的日志会自动存入按年份-月份建立的文件夹下面并进行压缩,作为存档-->
<RollingFile name="RollingFileWarn" fileName="${FILE_LOG_BASE_PATH}/warn.log" filePattern="${FILE_LOG_BASE_PATH}/WARN-%d{yyyy-MM-dd}_%i.log.gz">
<!--控制台只输出level及以上级别的信息(onMatch),其他的直接拒绝(onMismatch)-->
<ThresholdFilter level="warn" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout pattern="${FILE_LOG_PATTERN}"/>
<Policies>
<!--超过100M增加序号-->
<SizeBasedTriggeringPolicy size="10MB"/>
<!-- 每天滚动 -->
<TimeBasedTriggeringPolicy interval="1" modulate="true"/>
</Policies>
<DefaultRolloverStrategy>
<!-- 关键点:按时间删除旧文件(优先级高于max序号) -->
<Delete basePath="${FILE_LOG_BASE_PATH}" maxDepth="1">
<IfFileName regex="WARN-\d{4}-\d{2}-\d{2}_\d+\.log\.gz" /> <!-- 匹配压缩日志 -->
<IfLastModified age="180d" /> <!-- 180天前的文件 -->
</Delete>
<!-- 控制最大序号数(次要限制) -->
<Max>10</Max> <!-- 每个日期最多保留10个序号文件 -->
</DefaultRolloverStrategy>
</RollingFile>
<!-- 这个会打印出所有的error及以下级别的信息,每次大小超过size,则这size大小的日志会自动存入按年份-月份建立的文件夹下面并进行压缩,作为存档-->
<RollingFile name="RollingFileError" fileName="${FILE_LOG_BASE_PATH}/error.log" filePattern="${FILE_LOG_BASE_PATH}/ERROR-%d{yyyy-MM-dd}_%i.log.gz">
<!--控制台只输出level及以上级别的信息(onMatch),其他的直接拒绝(onMismatch)-->
<ThresholdFilter level="error" onMatch="ACCEPT" onMismatch="DENY"/>
<PatternLayout pattern="${FILE_LOG_PATTERN}"/>
<Policies>
<!--超过100M增加序号-->
<SizeBasedTriggeringPolicy size="10MB"/>
<!-- 每天滚动 -->
<TimeBasedTriggeringPolicy interval="1" modulate="true"/>
</Policies>
<DefaultRolloverStrategy>
<!-- 关键点:按时间删除旧文件(优先级高于max序号) -->
<Delete basePath="${FILE_LOG_BASE_PATH}" maxDepth="1">
<IfFileName regex="ERROR-\d{4}-\d{2}-\d{2}_\d+\.log\.gz" /> <!-- 匹配压缩日志 -->
<IfLastModified age="180d" /> <!-- 180天前的文件 -->
</Delete>
<!-- 控制最大序号数(次要限制) -->
<Max>10</Max> <!-- 每个日期最多保留10个序号文件 -->
</DefaultRolloverStrategy>
</RollingFile>
</Appenders>
<!--Logger节点用来单独指定日志的形式,比如要为指定包下的class指定不同的日志级别等。-->
<!--然后定义loggers,只有定义了logger并引入的appender,appender才会生效-->
<loggers>
<!--过滤掉spring和mybatis的一些无用的DEBUG信息-->
<Logger name="org.mybatis" level="info" additivity="false">
<AppenderRef ref="Console"/>
</Logger>
<!--监控系统信息-->
<!--若是additivity设为false,则 子Logger 只会在自己的appender里输出,而不会在 父Logger 的appender里输出。-->
<Logger name="org.springframework" level="info" additivity="false">
<AppenderRef ref="Console"/>
</Logger>
<Root level="info">
<Appender-ref ref="Console"/>
<Appender-ref ref="RollingFileInfo"/>
<Appender-ref ref="RollingFileWarn"/>
<Appender-ref ref="RollingFileError"/>
<Appender-ref ref="LogstashAsync"/> <!-- 如不需要其他日志打印,可只保留这个配置即可 -->
</Root>
</loggers>
</configuration>
测试并查看ELK日志
本地启动springboot项目,ELK会收集日志,可在平台上查看
新建日志视图
进入elastic平台
创建view
查看是否有对应索引信息
配置view信息
比如我需要查看api的所有日志,现在因为是按月分的索引索引我们可以把对应的全加上,用通配符
保持测试日志是否正常打印输出
好了,以上就是基础的elk的安装和使用了,赶紧试试吧。