超详细的ELK Stack构建微服务日志平台指南

本篇主要分享一下自己在物理机上搭建ELK+Filebeat采集服务日志的过程,其中ES和Logstash都是单节点的,在此之前我们先来熟悉下基本概念。

Elastic Stack 是什么?

Elastic Stack 是 Elastic 公司旗下一系列产品的合称,能够安全可靠地从任何来源获取任何格式的数据,然后对数据进行搜索、分析和可视化。其中包括 Elasticsearch、 Logstash、Kibana、Beats核心组件,早些年也被称为 "ELKB" , 后来考虑到技术的更新换代,官方统称为 "ELK Stack"(最新版本已将logstash和beats归为Integrations模块)

Elasticsearch 是一个搜索和分析引擎,是一种特殊的"存储库";Logstash 是服务器端数据处理通道,负责采集数据、转换数据、发送数据;Kibana 是一个让用户在 Elasticsearch 中使用图形和图标的数据可视化界面。 Beats是 Elastic 公司开发提供的开源数据收集器集合,只需要将其端(Agent)安装到服务器上,通过简单的配置,就可以将指定的数据发送到 Elasticsearch。Elastic 提供了多种类的 Beats 用来收集不同的数据。本篇搭建的微服务日志平台用到的是Filebeat

搭建过程

1.环境准备

官方下载地址,根据你的操作系统选择你需要的产品和版本。为了避免兼容性问题,es和Logstash请使用同一版本。

安装包 版本
jdk 1.8.0_181
elasticsearch-7.13.0-linux-x86_64.tar.gz 7.13.0
kibana-7.13.0-linux-x86_64.tar.gz 7.13.0
logstash-7.13.0-linux-x86_64.tar.gz 7.13.0
filebeat-7.13.0-linux-x86_64.tar.gz 7.13.0

Es8.xx需要jdk11,如果你是jdk8,选择7.xx版本。


服务 服务器
es 192.168.1.16
kibana 192.168.1.16
logstash 192.168.1.16
Filebeat 192.168.2.16
微服务 192.168.2.16

此外,提前确认你的机器以下端口是可以正常访问的,ES(9200,9300),kibana(5601),logstash(5044),一切准备就绪后,就可以开始我们的搭建了

2.ES部署

2.1 解压

shell 复制代码
tar -zxvf elasticsearch-7.13.0-linux-x86_64.tar.gz

2.2 配置文件

bash 复制代码
# 编辑es配置文件
vim config/elasticsearch.yml
yml 复制代码
# 集群名称
cluster.name: cluster1
# 初始主节点
cluster.initial_master_nodes: ["node-1"]
# 节点名
node.name: node-1
# 是否可选为主节点
node.roles: [master,data,remote_cluster_client]
# data文件夹,提前创建好
path.data: /var/local/elasticsearch_data
# 日志文件夹,提前创建好
path.logs: /var/local/elasticsearch_logs
# 对方暴露的ip地址
network.host: 192.168.1.16
# 允许跨域访问,head访问时需要开启
http.cors.enabled: true
http.cors.allow-origin: "*"

调整JVM参数

bash 复制代码
vim config/jvm.options
#更改堆内存
-Xms8g   
-Xmx8g

确认最大用户打开文件数

bash 复制代码
# 查看当前值 
ulimit -Hn
# 如果是4096可能会因为内存过小无法启动
# root执行指令 
vim /etc/security/limits.conf
# 文件末尾添加
root soft nproc 65536
root hard nproc 65536
root soft nofile 65536
root hard nofile 65536
elastic soft nproc 65536
elastic hard nproc 65536
elastic soft nofile 65536
elastic hard nofile 65536
# 重新连接终端,再次查看
ulimit -Hn

增加vm.max_map_count

bash 复制代码
vim /etc/sysctl.conf
# 最后添加 
vm.max_map_count=655360 
# 查看 
sysctl -p

2.3 启动

es和kibana不允许使用root账户使用,这里我们需要先创建一个用户elastic

bash 复制代码
sudo adduser elastic

设置用户密码

bash 复制代码
sudo passwd elastic

授权给elastic用户

bash 复制代码
chown -r elastic:elastic elasticsearch-7.13.0
chown -r elastic:elastic /var/local/elasticsearch_data/
chown -r elastic:elastic /var/local/elasticsearch_logs/

切换到elastic用户

bash 复制代码
su - elastic

启动es

bash 复制代码
# es安装目录下执行 
./bin/elasticsearch & 

2.4 测试

浏览器中访问http://192.168.1.16:9200 出现以下页面表示成功

3.kibana部署

3.1 解压

bash 复制代码
tar -zxvf kibana-7.13.0-linux-x86_64.tar.gz

3.2 修改配置文件

bash 复制代码
vim config/kibana.yml
yml 复制代码
server.host: "0.0.0.0"
server.port: 5601
server.name: kibana
elasticsearch.hosts: [ "http://192.168.212.16:9200"]
monitoring.ui.container.elasticsearch.enabled: true
#汉化
i18n.locale: "zh-CN"

3.3 启动

bash 复制代码
# Kibana也需要elastic账号启动
chown -r elastic elastic kibana-7.13.0-linux-x86_64
# 切换账户
su - elastic
# 启动
./bin/kibana &

3.4 验证

浏览器中访问http://192.168.1.16:5601 出现以下页面表示成功

4.logstash部署

4.1 解压

bash 复制代码
tar -zxvf logstash-7.13.0-linux-x86_64.tar.gz 

4.2 修改配置文件

bash 复制代码
vim config/logstash-sample.conf

4.2.1 配置input和output

yml 复制代码
input {
  beats {
    port => 5044
  }
}
# 输出日志的方式
output { 
# 按照日志标签对日志进行分类处理,日志标签后续会在filebeat中定义
 if "dev-log" in [tags] {
    elasticsearch {
    # es host
      hosts => ["http://192.168.1.16:9200"]
      # 索引名称
      index => "dev-log-%{+YYYY.MM.dd}"
    }
 }
 if "prod-log" in [tags] {
    elasticsearch {
      hosts => ["http://192.168.1.16:9200"]
      index => "prod-log-%{+YYYY.MM.dd}"
    }
 }
}

4.2.2 配置filter

在 Logstash 中,过滤器用于处理从输入源接收到的数据,对数据进行解析、转换、过滤等操作,然后将处理后的数据发送到输出目的地。过滤器配置通常包含在 Logstash 配置文件的 filter 部分中。

yml 复制代码
filter {
  grok {
    match => {
      "message" => [
        "%{TIMESTAMP_ISO8601:timestamp} \[%{DATA:project}\]\[%{DATA:sysId}\]\[%{DATA:thread}\] %{LOGLEVEL:log.level} %{DATA:class}:%{NUMBER:line} - \[%{DATA:traceId}\]\[%{DATA:appName}\]\[%{DATA:userId}\] %{GREEDYDATA:message}"
      ]
    }
  }
  date {
    match => [ "timestamp", "yyyy-MM-dd HH:mm:ss.SSS" ]
  }

  mutate {
    remove_field => ["@version", "host", "agent", "ecs", "input"]
  }
}
  1. grok 过滤器:

    • match 字段定义了一个 grok 模式,用于解析日志行的各个部分。该模式包含了多个具名捕获组,用于从日志行中提取各个字段的值。
    • 例如,%{TIMESTAMP_ISO8601:timestamp} 用于匹配 ISO8601 格式的时间戳,并将其存储在名为 timestamp 的字段中。

可以看到我使用了match对我的日志进行了关键字的提取,这些关键字可以作为es的字段存储在es文档中,后续可以在kibana使用这些字段进行检索。

  1. date 过滤器:

    • 用于将字符串格式的时间戳转换为 Elasticsearch 接受的日期格式。在配置中,timestamp 字段被解析为日期,并且 match 字段指定了时间戳的输入格式。
  2. mutate 过滤器:

    • remove_field 选项用于删除指定的字段,以清理事件中的不需要的字段。在这里,删除了 @versionhostagentecsinput 字段。

4.2.3 指定template

在 Logstash 中执行 Elasticsearch 索引的模板(template)时,通常是通过 elasticsearch 输出插件的 template 选项来实现的。这个选项允许你指定一个 JSON 文件,其中包含了 Elasticsearch 索引的映射、设置等信息。

yml 复制代码
output {
  elasticsearch {
    hosts => ["your_elasticsearch_host"]
    index => "your_index_name-%{+YYYY.MM.dd}"  # 根据需要定义索引结构
    template => "/path/to/your/template.json"  # 指定模板文件的路径
    template_name => "your_template_name"  # 指定模板的名称
  }
}

在上述示例中:

  • template 选项指定了 Elasticsearch 索引模板的 JSON 文件路径。
  • template_name 选项指定了该模板的名称。

然后,你需要创建一个 JSON 文件,其中包含 Elasticsearch 索引的映射信息。模板文件类似于下面的示例:

yml 复制代码
{
  "template": "dev-log-*",
  "order": 1,
  "settings": {
    "number_of_shards": 1,
    # 如果es是单节点分片数为1 这里设置一下 索引的副本数为0
    "number_of_replicas": 0,
    "refresh_interval": "60s",
    "index.max_result_window": 10000000,
    "index.blocks.read_only_allow_delete": null
  },
  "mappings": {
      "properties": {
        "project": {
          "type": "keyword"
        },
        "appName": {
          "type": "keyword"
        },
        "traceId": {
          "type": "keyword"
        },
        "userId": {
          "type": "keyword"
        },
        "class": {
          "type": "keyword"
        },
        "log.level": {
          "type": "text"
        },
        "log.file.path": {
          "type": "text"
        },
        "message": {
          "type": "text"
        },

        "sysId": {
          "type": "keyword"
        },
        "thread": {
          "type": "keyword"
        },

        "line": {
          "type": "keyword"
        }
      }
    
  }
}

如此一来,logstash会按照你自定义的结构,向es中写入数据。 除了指定在配置文件中指定template,我们还可以再kibana中开发工具里,执行脚本也可以设置索引模版

bash 复制代码
GET _template/logstash

PUT _template/logstash
{
  "index_patterns": ["dev-*", "prod-*"],
  "settings": {
    "number_of_shards": 1,
    "number_of_replicas": 0
  },
  "mappings": {
      "properties": {
        "project": {
          "type": "keyword"
        },
        "appName": {
          "type": "keyword"
        },
        "traceId": {
          "type": "keyword"
        },
        "userId": {
          "type": "keyword"
        },
        "class": {
          "type": "keyword"
        },
        "log.level": {
          "type": "text"
        },
        "log.file.path": {
          "type": "text"
        },
        "message": {
          "type": "text"
        },

        "sysId": {
          "type": "keyword"
        },
        "thread": {
          "type": "keyword"
        },

        "line": {
          "type": "keyword"
        }
      }
    
  }
}

或者在索引管理中对索引模版进行配置

4.3 启动

bash 复制代码
./bin/logstash -f config/logstash-sample.conf &

5.filebeat部署

Filebeat需要和服务部署在一起,也就是需要采集什么数据就在哪部署。

5.1 解压

bash 复制代码
tar -zxvf filebeat-7.13.0-linux-x86_64

5.2 修改配置文件

bash 复制代码
vim filebeat.yml
yml 复制代码
# 从日志文件输入日志
filebeat.inputs:
- type: log
  enabled: true
  paths:
    - /your/path/xx.log
    - /your/path2/xx.log
  # 定义日志标签
  tags: ["dev-log"]
  multiline.pattern: '^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}.\d{3}'
  multiline.negate: true
  multiline.match: after

# 输出到logstash
output.logstash:
# logstash所在服务器的ip和端口
  hosts: ["192.168.1.16:5044"]
# 默认配置,不做改动
processors:
  - add_host_metadata:
      when.not.contains.tags: forwarded
  - add_cloud_metadata: ~
  - add_docker_metadata: ~
  - add_kubernetes_metadata: ~
  1. filebeat.inputs 部分:

    • type: log:指定输入类型为日志文件。
    • enabled: true:启用输入。
    • paths:指定要监视的日志文件路径。
    • tags:为事件添加标签,这里是 "dev-log"。
    • multiline.pattern:定义多行日志的正则表达式。
    • multiline.negate:如果设置为 true,则表示只有不匹配 pattern 的行会合并到上一行。
    • multiline.match:定义匹配行的位置,这里是 "after",表示匹配行在下一行。
  2. output.logstash 部分:

    • hosts:指定 Logstash 服务器的地址和端口。
  3. processors 部分:

    • 包含了一系列处理器,用于添加主机元数据、云元数据、Docker 元数据和 Kubernetes 元数据。

5.3 启动

bash 复制代码
# -e 调试模式 会将日志输出到控制台
 ./filebeat -e -c filebeat.yml & 

Kibana配置

完成前面的操作后,此时日志已经通过Filebeat采集传输到Logstash中,然后经过我们的过滤写入了es。如果想在kibana上查看这些数据,还需要进行一些配置。

在索引管理中选择索引模式,索引模式用来匹配我们的es索引数据。

设置成功就可以根据索引模式去筛选我们的索引数据了

相关推荐
gma9993 小时前
【BUG】ES使用过程中问题解决汇总
大数据·elasticsearch·搜索引擎
vvw&5 小时前
如何在 Ubuntu 22.04 上安装带有 Nginx 的 ELK Stack
linux·运维·nginx·ubuntu·elk·elasticsearch·开源项目
Elastic 中国社区官方博客10 小时前
使用 Elastic AI Assistant for Search 和 Azure OpenAI 实现从 0 到 60 的转变
大数据·人工智能·elasticsearch·microsoft·搜索引擎·ai·azure
Karoku06616 小时前
【企业级分布式系统】ELK优化
运维·服务器·数据库·elk·elasticsearch
上优18 小时前
uniapp 选择 省市区 省市 以及 回显
大数据·elasticsearch·uni-app
jwolf220 小时前
Elasticsearch向量搜索:从语义搜索到图搜图只有一步之遥
elasticsearch·搜索引擎·ai
你可以叫我仔哥呀21 小时前
ElasticSearch学习笔记三:基础操作(一)
笔记·学习·elasticsearch
hummhumm1 天前
第 25 章 - Golang 项目结构
java·开发语言·前端·后端·python·elasticsearch·golang
java1234_小锋1 天前
Elasticsearch中的节点(比如共20个),其中的10个选了一个master,另外10个选了另一个master,怎么办?
大数据·elasticsearch·jenkins
Elastic 中国社区官方博客1 天前
Elasticsearch 开放推理 API 增加了对 IBM watsonx.ai Slate 嵌入模型的支持
大数据·数据库·人工智能·elasticsearch·搜索引擎·ai·全文检索