前言

今天来介绍 go-zero 生态的另一个组件 go-stash。这是一个 logstash 的 Go 语言替代版,我们用 go-stash 相比原先的 logstash 节省了2/3的服务器资源。如果你在用 logstash,不妨试试,也可以看看基于 go-zero 实现这样的工具是多么的容易,这个工具作者仅用了两天时间。

整体架构

先从它的配置中,我们来看看设计架构。

Clusters:
- Input:
Kafka:
# Kafka 配置 --> 联动 go-queue
Filters:
# filter action
- Action: drop
- Action: remove_field
- Action: transfer
Output:
ElasticSearch:
# es 配置 {host, index}

看配置名:kafka 是数据输出端,es 是数据输入端,filter 抽象了数据处理过程。

对,整个 go-stash 就是如 config 配置中显示的,所见即所得。

启动

stash.go 的启动流程大致分为几个部分。因为可以配置多个 cluster,那从一个 cluster 分析:

  1. 建立与 es 的连接【传入 es 配置】
  2. 构建 filter processorses 前置处理器,做数据过滤以及处理,可以设置多个】
  3. 完善对 es 中 索引配置,启动 handle ,同时将 filter 加入handle【处理输入输出】
  4. 连接下游的 kafka,将上面创建的 handle 传入,完成 kafkaes 之间的数据消费和数据写入

MessageHandler

在上面架构图中,中间的 filter 只是从 config 中看到,其实更详细是 MessageHandler 的一部分,做数据过滤和转换,下面来说说这块。

以下代码:https://github.com/tal-tech/go-stash/tree/master/stash/handler/handler.go

type MessageHandler struct {
writer *es.Writer
indexer *es.Index
filters []filter.FilterFunc
}

这个就对应上面说的,filter 只是其中一部分,在结构上 MessageHandler 是对接下游 es ,但是没有看到对 kafka 的操作。

别急,从接口设计上 MessageHandler 实现了 go-queueConsumeHandler 接口。

这里,上下游就串联了:

  1. MessageHandler 接管了 es 的操作,负责数据处理到数据写入
  2. 对上实现了 kafkaConsume 操作。这样在消费过程中执行 handler 的操作,从而写入 es

实际上,Consume() 也是这么处理的:

func (mh *MessageHandler) Consume(_, val string) error {
var m map[string]interface{}
// 反序列化从 kafka 中的消息
if err := jsoniter.Unmarshal([]byte(val), &m); err != nil {
return err
}
// es 写入index配置
index := mh.indexer.GetIndex(m)
// filter 链式处理【因为没有泛型,整个处理都是 `map进map出`】
for _, proc := range mh.filters {
if m = proc(m); m == nil {
return nil
}
}
bs, err := jsoniter.Marshal(m)
if err != nil {
return err
}
// es 写入
return mh.writer.Write(index, string(bs))
}

数据流

说完了数据处理,以及上下游的连接点。但是数据要从 kafka -> es ,数据流出这个动作从 kafka 角度看,应该是由开发者主动 pull data from kafka

那么数据流是怎么动起来?我们回到主程序 https://github.com/tal-tech/go-stash/blob/master/stash/stash.go

其实 启动 整个流程中,其实就是一个组合模式:

func main() {
// 解析命令行参数,启动优雅退出
...
// service 组合模式
group := service.NewServiceGroup()
defer group.Stop() for _, processor := range c.Clusters {
// 连接es
...
// filter processors 构建
...
// 准备es的写入操作 {写入的index, 写入器writer}
handle := handler.NewHandler(writer, indexer)
handle.AddFilters(filters...)
handle.AddFilters(filter.AddUriFieldFilter("url", "uri"))
// 按照配置启动kafka,并将消费操作传入,同时加入组合器
for _, k := range toKqConf(processor.Input.Kafka) {
group.Add(kq.MustNewQueue(k, handle))
}
}
// 启动这个组合器
group.Start()
}

整个数据流,就和这个 group 组合器有关了。

group.Start()
|- group.doStart()
|- [service.Start() for service in group.services]

那么说明加入 groupservice 都是实现 Start()。也就是说 kafka 端的启动逻辑在 Start()

func (q *kafkaQueue) Start() {
q.startConsumers()
q.startProducers() q.producerRoutines.Wait()
close(q.channel)
q.consumerRoutines.Wait()
}
  1. 启动 kafka 消费程序
  2. 启动 kafka 消费拉取端【可能会被名字迷惑,实际上是从 kafka 拉取消息到 q.channel
  3. 消费程序终止,收尾工作

而我们传入 kafka 中的 handler,上文说过其实是 Consume,而这个方法就是在 q.startConsumers() 中执行的:

q.startConsumers()
|- [q.consumeOne(key, value) for msg in q.channel]
|- q.handler.Consume(key, value)

这样整个数据流就彻底串起来了:

总结

作为 go-stash 第一篇文章,本篇从架构和设计上整体介绍 go-stash ,有关性能和为什么我们要开发一个这样的组件,我们下篇文章逐渐揭晓。

https://github.com/tal-tech/go-stash

关于 go-zero 更多的设计和实现文章,可以持续关注我们。

https://github.com/tal-tech/go-zero

欢迎使用 go-zero 并 star 支持我们!

微信交流群

关注『微服务实践』公众号并回复 进群 获取社区群二维码。

极速精简 Go 版 Logstash的更多相关文章

  1. 新萝卜家园GHOST WIN7系统32,64位极速装机特别版

    系统来自:系统妈:http://www.xitongma.com 新萝卜家园GHOST win7系统32位极速装机特别版 V2016年3月 系统概述 新萝卜家园ghost win7系统32位极速装机特 ...

  2. 通用PE工具箱 4.0精简优化版

    通用PE工具箱 4.0精简优化版 经用过不少 WinPE 系统,都不是很满意,普遍存在篡改主页.添加广告链接至收藏夹.未经允许安装推广软件等流氓行为,还集成了诸多不常用的工具,令人头疼不已.那么今天给 ...

  3. 搜狗拼音输入法 V9.1.0.2589 最新去广告精简优化版

    搜狗拼音输入法9.0 正式版例行发布,最新版字母代号b,详细版本号为v9.1.0.2589:搜狗拼音输入法是电脑装机必备软件,版本有传统版和智慧版之分,其打字超准.词库超大.速度飞快.外观漂亮,因此使 ...

  4. VMware Workstation 14.1.1 精简特别版

    VMware Workstation 精简特别版,由卡饭网友のcuiplay精简制作,集成许可证密钥安装即永久激活,该特别版最大特色可安装MAC OS X客户操作系统,此外添加了DELL SLIC 2 ...

  5. 【ZZ】Visual C++ 6.0 精简安装版(支持VA、ICC 等等安装)

    (2012-04-22 08:10:10) 标签: it 分类: 软件_Software Visual C++ 6.0 精简安装版(支持VA.ICC 等等安装) 2012-04-16 21:07 想找 ...

  6. Visual C++ 6.0精简绿色版下载及简单使用教程

    Visual C++ 6.0精简绿色版下载及简单使用教程 Microsoft Visual C++简介 Visual Studio 是微软公司推出的开发环境,Visual Studio 可以用来创建 ...

  7. 精简Command版SqlHelper

    我在写CSharp程序对数据库进行操作时发现Connection对象起到了连接数据库的做用,实际执行SQL语句使用的是Command对象的方法,所以对SqlHelper进行了重写,具体如下: 一.创建 ...

  8. oracle客户端精简绿色版-环境变量配置

    大型项目开发中,常用的数据库,当属Oracle.但Oracle 客户端安装就要一张光盘,体积很大.而且安装后,基本上就用2个功能:TNS配置服务名,SqlPlus.在开发过程中,大量使用Toad和PL ...

  9. Oracle 精简绿色版客户端的配置

    在项目开发中常常用到Oracle.但Oracle 客户端体积很大.安装后,主要用的就1个功能:TNS配置服务名,偶尔用到SqlPlus.在开发过程中,大量使用Navicate和PL/SQL Devel ...

随机推荐

  1. 为什么国内的好多具备 HTTPS 的网站却没有使用 HTTPS 重定向功能

    为什么国内的好多具备 HTTPS 的网站却没有使用 HTTPS 重定向功能 HTTPS 重定向 good demos ️ HTTPS http://www.xgqfrms.xyz/ https://w ...

  2. EventEmitter & custom events & sub/pub

    EventEmitter & custom events & sub/pub https://repl.it/@xgqfrms/PPLabs-frontend-answers // 5 ...

  3. Flutter 避免阻塞ui线程

    import 'dart:async'; import 'dart:isolate'; import 'package:flutter/material.dart'; import 'package: ...

  4. 09、IO流—File类与IO流

    目录 一.File类 基本认识 实用方法 获取功能 重命名功能(包含剪切) 判断功能 创建.删除文件 实际小案例 二.IO流 1.认识IO流 2.IO流基类介绍 字节流基类介绍 字符流基类介绍 三.节 ...

  5. Java魔法类:Unsafe应用解析

    本文转载自Java魔法类:Unsafe应用解析 前言 Unsafe是位于sun.misc包下的一个类,主要提供一些用于执行低级别.不安全操作的方法,如直接访问系统内存资源.自主管理内存资源等,这些方法 ...

  6. vue子组件的样式没有加scoped属性会影响父组件的样式

    scoped是一个vue的指令,用来控制组件的样式生效区域,加上scoped,样式只在当前组件内生效,不加scoped,这个节点下的样式会全局生效. 需要注意的是:一个组件的样式肯定是用来美化自己组件 ...

  7. Lambad表达式--Java8新特性

    1.概述 Lambda是一个匿名函数,是java8的一个新特性.可以对接口进行非常简洁的实现.但它要求接口中只能有一个抽象方法,原因是lambda只能实现一个方法.另外,需要在接口上添加注解@Func ...

  8. 解决使用Redis时配置 fastjson反序列化报错 com.alibaba.fastjson.JSONException: autoType is not support

    1.问题描述 在使用redis时,配置自定义序列化redisTemplate为FastJsonRedisSerializer .  1 /** 2 * 自定义redis序列化器 3 */ 4 @Sup ...

  9. 剑指 Offer 56 - I. 数组中数字出现的次数 + 分组异或

    剑指 Offer 56 - I. 数组中数字出现的次数 Offer_56_1 题目描述 解题思路 java代码 /** * 方法一:数位方法 */ class Offer_56_1_2 { publi ...

  10. Microsoft Teams 最新功能发布:协作篇

    正在进行的2021年的Microsoft Ignite大会,发布了一系列跟Microsoft Teams相关的新功能,英文介绍请参考 https://techcommunity.microsoft.c ...