
使用读写分离模式扩展 Grafana Loki
作者 |阳明
来源 | k8s技术圈(ID:kube100)
Loki 由多个微服务组件构建而成,可以作为一个可水平扩展的分布式系统运行,Loki 的独特设计可以将整个分布式系统的代码编译成单个二进制或 Docker 映像,单个二进制文件的行为由 -target 命令行标志控制。
单体模式
最简单的操作模式是设置 -target=all,这是默认的方式,不需要指定,这就是单体模式,它以单个二进制文件或 Docker 映像的形式在单个进程中运行 Loki 的所有微服务组件。单体模式对于快速开始使用 Loki 以及每天数据量约100GB的读写量非常有用。将单体模式部署水平扩展至更多实例可以通过使用共享对象存储,配置 memberlist_config 属性在所有实例之间共享状态。
可以通过使用 memberlist_config 配置和共享对象存储运行两个 Loki 实例来配置高可用性。以循环方式将流量路由到所有 Loki 实例。并行查询受限于实例数量和定义的查询并行度。
单体模式的安装非常简单,直接使用 grafana/loki-stack 这个 Helm Chart 包安装即可。
读写分离模式
如果你每天的日志量超过几百 GB,或者你想进行读写分离,Loki 提供了简单的可扩展部署模式。这种部署模式可以扩展到每天数 TB 甚至更多的日志。在这种模式下,Loki 的组件微服务被绑定到两个目标中:-target=read 和 -target=write,BoltDB compactor 服务将作为读取目标的一部分运行。
分离读写路径有以下优点:
- 通过提供专用节点提高写入路径的可用性
- 可单独扩展读取路径以按需添加/删除查询性能
这种读写分离的模式需要在 Loki 前面有一个负载均衡器,它将 /loki/api/v1/push 流量路由到写入节点,所有其他请求都转到读取节点,流量应该以循环方式发送。
安装
我们同样使用 Helm Chart 进行安装,首先获取读写分离模型的 Chart 包:
该 Chart 包支持下表中显示的组件,Ingester、distributor、querier 和 query-frontend 都会安装,其他组件是可选的。
这里我们使用 MinIO 来作为远程数据存储,分别配置读和写的 Loki 实例副本数为2,为了在 Loki 前面添加一个负载均衡器,需要开启 Gateway,对应的 Values 文件如下所示:
然后使用上面的 values 文件来安装读写分离模式的 Loki:
安装完成后查看 Pod 状态是否正常:
可以看到分别部署了两个副本的 write 和 read 的 Loki,另外还有一个 gateway 的 Pod,gateway 实际上就是一个 nginx 应用,用来将 /loki/api/v1/push 请求路由到 write 节点去,我们可以查看 gateway 的配置来验证:
上面就是一个典型的 Nginx 配置,从配置可以看出会把请求 /api/prom/push 和 /loki/api/v1/push 这两个 Push API 代理到 http://loki-write.logging.svc.cluster.local:3100$request_uri;,也就是上面的两个 loki-write 节点,而读取相关的接口被代理到 loki-read 节点,然后 loki-write 启动参数配置 -target=write, loki-read 启动参数配置 -target=read,这样去实现读写分离。不过读写的应用是共享同一个配置文件的,如下所示:
其中 common.storage.s3 指定的是 MinIO 的相关配置,通过 memberlist.join_members 来指定成员,其实就是所有的读写节点:
到这里我们就完成了 Loki 读写分离模式的部署。
Promtail写数据
为了验证应用是否正常,接下来我们再安装 Promtail 和 Grafana 来进行数据的读写。
获取 promtail 的 Chart 包并解压:
创建一个如下所示的 values 文件:
注意我们需要将 Promtail 中配置的 Loki 地址为 http://loki-gateway/loki/api/v1/push,这样就是 Promtail 将日志数据首先发送到 Gateway 上面去,然后 Gateway 根据我们的 Endpoints 去转发给 write 节点,使用上面的 values 文件来安装 Promtail:
正常安装完成后会在每个节点上运行一个 promtail:
正常 promtail 就已经在开始采集所在节点上的所有容器日志了,然后将日志数据 Push 给 gateway,gateway 转发给 write 节点,我们可以查看 gateway 的日志:
可以看到 gateway 现在在一直接接收着 /loki/api/v1/push 的请求,也就是 promtail 发送过来的,正常来说现在日志数据已经分发给 write 节点了,write 节点将数据存储在了 minio 中,可以去查看下 minio 中已经有日志数据了,前面安装的时候为 minio 服务指定了一个 32000 的 NodePort 端口:登录信息为:
accessKey: enterprise-logs
secretKey: supersecret
可以看到 minio 的 chunks 这个 bucket 中并没有日志数据,这是因为上面我们创建的 bucket 默认只有读取的权限,我们可以将该 bucket 修改为具有读写的权限:
正常修改后就会产生一个 fake 的目录了,这是默认没有提供多租户的数据目录,该目录下面存储着日志的 chunk 数据:
这是 Loki 日志的写入的路径。
Grafana读数据
下面我们来验证下读取路径,安装 Grafana 对接 Loki:
创建如下所示的 values 配置文件:
直接使用上面的 values 文件安装 Grafana:
可以通过上面提示中的命令获取登录密码:
然后使用上面的密码和 admin 用户名登录 Grafana:登录后进入 Grafana 添加一个数据源,这里需要注意要填写 gateway 的地址 http://loki-gateway:
保存数据源后,可以进入 Explore 页面过滤日志,比如我们这里来实时查看 gateway 这个应用的日志,如下图所示:
如果你能看到最新的日志数据那说明我们部署成功了读写分离模式的 Loki,读写分离模式可以大大提高 Loki 的性能和容量,如果这种模式还不能满足你的数据量,那么可以使用微服务模式来部署 Loki 了,未完待续......
