实时统一日志采集Flume平台化

      针对原生Flume在生产环境中暴露的问题,在开源Flume1.6.0版本上做了深度定制和部门内部统一推广:

  1.  与开源版本区别

模块

       Flume1.6

  Flumex-Agent

 

 

 

 

 

功能

1.低侵入性:

会对业务方日志文件重命名

1.无侵入性

2.休眠轮询: 占用线程&&限制采集文件的并行度

2.轻量级:基于Linux的inotify机制采集

3.数据不完整性:基于file的full-name采集

3.数据完整性:基于inode的日志采集

4.不支持目录递归

4.支持目录递归

性能(单文件吞吐)

2M/s: 按行或byte采集,效率低

10M/s: 根据采集进度按byte或block动态采集

 

        运营

1.状态被动收集:自身基于server端服务的定向请求

1.状态主动推送:基于client端的状态心跳推送

2.无采集元数据备份

2.采集日志元数据备份:

可以记录和查询历史任一时间段内采集的文件列表、 文件数及采集文件的size、offset信息

2. 功能扩展

   2.1. 支持file-channel可靠性采集模式

      目前由于file-channel采集性能瓶颈, 所以采用memory-channel模式,两者采集能力对比如下:但memory-channel是会在服务异常中断或宕机场景时存在着日志丢失的风险。产品线上计划数据可靠性优先,所以会采用file-channel模式,其次对采集效率进行优化。

channel方式

readByByte
(events/s)

memory-channel

1800

file-channel

1400

   2.2. 支持单实例多目录多topic采集方式

        目前支持单topic的日志采集,待支持类似向上多topic多目录的并行采集,配置初步设计如下:

agent.sources.s1.topicGroups = t1 t2
agent.sources.s1.topicGroups.t1.topic = topic1
agent.sources.s1.topicGroups.t1.files = /home/logs/14505/^stat\.log*,/home/logs/stat/^monitor.log$

agent.sources.s1.topicGroups.t2.topic = topic2
agent.sources.s1.topicGroups.t2.files = /home/14505-1/^stat\.log$

   2.3 支持采集消息的定制字段追加,如host、appid等

       由于上游agent采集的业务应用方较多,为了方便下游离线或实时地对消息进行分类统计分析,对采集消息的内容,agent具有进行有约束的制定字段增加功能。 增加的定制字段有:a既定的变量, 如appid、t、host。

        a. 配置样例如下:

            %{appid}%{t}%{host}%{data}

        b. 相应消息样例如下:

            appid= test- product` t=1479089921875`host=localhost`deviceId=VSMjTvvy9CgDAE`messageId=`action=register_dt`logTime=1477911600905`msgCount=1`

3. 性能改善

   3.1. 目的

      a.  采用可靠性file-channel采集模式,保证采集数据的稳定性、日志可靠性(不丢失);

      b.  提升file-channel采集模式日志采集效率,提升5倍。 目前测试单日志文件memory模式采集能力1800行/S;

      c. 支持异步memory-channel性能采集模式,提升20倍采集效率。

   3.2. 目前现状

       采集的方式与flume原生的tail-log采集方式类似,按Byte逐行读取的采集模式; 当 file-offset ≈ file-size时,即日志文件的消费速率与其内容的生产效率相当时,这样可以保证log采集的实时性; 实测其性能  1500Events/s。

   3.3. 存在问题 
      但其存在性能瓶颈:假设机械磁盘的一次顺序读时间0.01ms,每行消息内容100个Bytes,则其IOPS性能上限:100000个Bytes/s = 1000Events/s; 所以当file-offset << file-size时,特别是在采集业务高峰时nginx运营日志情景时,会出现日志文件的消费速率会远小于其内容的生产效率,导致采集消息严重滞后。

   3.4. 修改策略
         采用实时动态调整采集方式的策略:
         a. 当file-offset ≈ file-size时,采用readByByte采集模式;
         b. 当file-offset << file-size时,采用readByBlock采集模式,提高采集吞吐量。
   3.5. 优化后结果对比

channel方式

readByByte
(events/s)

readByBlock
(events/s)

memory-channel

1800

20000

file-channel

1400

15000

    3.6.  支持同步/异步两种采集模式

        另外,采集每批消息耗时主要由三部分组成: read-log(1ms) + write-channel(1ms) + write-metaDB(4ms)。为了保证数据可靠性:每一批读取日志数据后的游标元信息会sync同步到sqlite中,其耗时占比达60%,所以每批消息的大头在write-metaDB操作上。

        为了支持不同的业务场景需求,服务支持”性能模式”,支持write-metaDB的异步写模式,同时会在异常关机情况时的数据丢失。下面是两种采集模式的采集效率对比:                                   

 采集模式

采集效率

吞吐能力

可靠模式(同步)

15000行/s

1.5M/s

性能模式(异步)

100000行/s

10M/s

  3.7. 消息大小与采集能力关系图

      线上服务已“可靠性”优先,所以会采用可靠模式。下面实验可靠模式下:不同消息字节大小与服务采集能力的关系图: 

 

4. 产品服务化

 4.1. 监控模块

      支持source输入与sink输出两维度信息的状态内容汇报,采集agent周期性地汇报采集状态给dashboard服务中心, 上传字段内容以Json格式上报。心跳周期:1min;传输协议:http-post。上报字段说明如下:

       a. 汇报状态字段说明

字段

说明

host

采集点的机器名或ip名

appId

采集日志的业务标示

receivedEventCount

探测接收到的事件数

acceptedEventCount

成功录入的事件数

receivedBatchCount

探测接收到的事件批次数

acceptedBatchCount

成功录入的事件批次数

attemptSendEventCount

尝试下游发送的事件数

successSendEventCount

成功下游发送的事件数

acceptedWindowEventCount

一个时间窗口接收到的事件数

sendWindowEventCount

一个时间窗口发送出的事件数

         b. 汇报状态字段样例 

{
     "host":"uaerouter5-vm01",
     "appId":"test-new-product",
     "receivedEventCount":"137136",
     "acceptedEventCount":"137136",
     "receivedBatchCount":"4073",
     "acceptedBatchCount":"4073",
     "attemptSendEventCount":"137136",
     "successSendEventCount":"137136",                
"acceptedWindowEventCount": "11000", "sendWindowEventCount": "10000“ }

   4.2. 配置与部署

     a. 支持本地配置的参数变化&动态监听&程序模块级别重启 

     b. 支持配置中心的统一程序包分发与部署   

 

posted @ 2017-02-07 15:58  gisorange  阅读(6386)  评论(2编辑  收藏  举报