Flume HDFS Sink常用配置深度解读

一般使用hdfs sink都会采用滚动生成文件的方式,hdfs sink滚动生成文件的策略有:

  • 基于时间
  • 基于文件大小
  • 基于hdfs文件副本数(一般要规避这种情况)
  • 基于event数量
  • 基于文件闲置时间

下面将详细讲解这些策略的配置以及原理

基于时间策略

配置项:hdfs.rollInterval
默认值:30秒
说明:如果设置为0表示禁用这个策略
原理:
org.apache.flume.sink.hdfs.BucketWriter.append方法中打开一个文件,都会调用open方法,如果设置了hdfs.rollInterval,那么hdfs.rollInterval秒之内只要其他策略没有关闭文件,文件会在hdfs.rollInterval秒之后关闭。

// if time-based rolling is enabled, schedule the roll
if (rollInterval > 0) {
  Callable<Void> action = new Callable<Void>() {
    public Void call() throws Exception {
      LOG.debug("Rolling file ({}): Roll scheduled after {} sec elapsed.",
          bucketPath, rollInterval);
      try {
        // Roll the file and remove reference from sfWriters map.
        close(true);
      } catch (Throwable t) {
        LOG.error("Unexpected error", t);
      }
      return null;
    }
  };
  timedRollFuture = timedRollerPool.schedule(action, rollInterval,
      TimeUnit.SECONDS);
}

基于文件大小和event数量策略

配置项:

  1. 文件大小策略:hdfs.rollSize
  2. event数量策略:hdfs.rollCount

默认值:

  1. 文件大小策略:1024字节
  2. event数量策略:10

说明:如果设置为0表示禁用这些策略
原理:
这2种策略都是在org.apache.flume.sink.hdfs.BucketWriter.shouldRotate方法中进行判断的,只要doRotate的值为true,那么当前文件就会关闭,即滚动到下一个文件。

private boolean shouldRotate() {
  boolean doRotate = false;

//判断文件副本数
  if (writer.isUnderReplicated()) {
    this.isUnderReplicated = true;
    doRotate = true;
  } else {
    this.isUnderReplicated = false;
  }

//判断event数量
  if ((rollCount > 0) && (rollCount <= eventCounter)) {
    LOG.debug("rolling: rollCount: {}, events: {}", rollCount, eventCounter);
    doRotate = true;
  }

//判断文件大小
  if ((rollSize > 0) && (rollSize <= processSize)) {
    LOG.debug("rolling: rollSize: {}, bytes: {}", rollSize, processSize);
    doRotate = true;
  }

  return doRotate;
}

注意:如果同时配置了时间策略和文件大小策略,那么会先判断时间,如果时间没到再判断其他的条件。

基于hdfs文件副本数

配置项:hdfs.minBlockReplicas
默认值:和hdfs的副本数一致
原理:
从上面的代码中可以看到,判断副本数的关键方法是writer.isUnderReplicated(),即

public boolean isUnderReplicated() {
  try {
    int numBlocks = getNumCurrentReplicas();
    if (numBlocks == -1) {
      return false;
    }
    int desiredBlocks;
    if (configuredMinReplicas != null) {
      desiredBlocks = configuredMinReplicas;
    } else {
      desiredBlocks = getFsDesiredReplication();
    }
    return numBlocks < desiredBlocks;
  } catch (IllegalAccessException e) {
    logger.error("Unexpected error while checking replication factor", e);
  } catch (InvocationTargetException e) {
    logger.error("Unexpected error while checking replication factor", e);
  } catch (IllegalArgumentException e) {
    logger.error("Unexpected error while checking replication factor", e);
  }
  return false;
}

也就是说,如果当前正在写的文件的副本数小于hdfs.minBlockReplicas,此方法返回true,其他情况都返回false假设这个方法返回true,那么看一下会发生什么事情。
首先就是上面代码提到的shouldRotate方法肯定返回的是true。再继续跟踪,下面的代码是关键

// check if it's time to rotate the file
if (shouldRotate()) {
  boolean doRotate = true;

  if (isUnderReplicated) {
    if (maxConsecUnderReplRotations > 0 &&
        consecutiveUnderReplRotateCount >= maxConsecUnderReplRotations) {
      doRotate = false;
      if (consecutiveUnderReplRotateCount == maxConsecUnderReplRotations) {
        LOG.error("Hit max consecutive under-replication rotations ({}); " +
            "will not continue rolling files under this path due to " +
            "under-replication", maxConsecUnderReplRotations);
      }
    } else {
      LOG.warn("Block Under-replication detected. Rotating file.");
    }
    consecutiveUnderReplRotateCount++;
  } else {
    consecutiveUnderReplRotateCount = 0;
  }

  if (doRotate) {
    close();
    open();
  }
}

这里maxConsecUnderReplRotations是固定的值30,也就是说,文件滚动生成了30个之后,就不会再滚动了,因为将doRotate设置为了false。所以,从这里可以看到,如果isUnderReplicated方法返回的是true,可能会导致文件的滚动和预期的不一致。规避这个问题的方法就是将hdfs.minBlockReplicas设置为1,一般hdfs的副本数肯定都是大于等于1的,所以isUnderReplicated方法一定会返回false
所以一般情况下,要规避这种情况,避免影响文件的正常滚动。

基于文件闲置时间策略

配置项:hdfs.idleTimeout
默认值:0
说明:默认启动这个功能
这种策略很简单,如果文件在hdfs.idleTimeout秒的时间里都是闲置的,没有任何数据写入,那么当前文件关闭,滚动到下一个文件。

public synchronized void flush() throws IOException, InterruptedException {
  checkAndThrowInterruptedException();
  if (!isBatchComplete()) {
    doFlush();

    if (idleTimeout > 0) {
      // if the future exists and couldn't be cancelled, that would mean it has already run
      // or been cancelled
      if (idleFuture == null || idleFuture.cancel(false)) {
        Callable<Void> idleAction = new Callable<Void>() {
          public Void call() throws Exception {
            LOG.info("Closing idle bucketWriter {} at {}", bucketPath,
                     System.currentTimeMillis());
            if (isOpen) {
              close(true);
            }
            return null;
          }
        };
        idleFuture = timedRollerPool.schedule(idleAction, idleTimeout,
            TimeUnit.SECONDS);
      }
    }
  }
}

注:本文使用的源码版本为flume-1.7.0

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 141,469评论 1 298
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 60,715评论 1 254
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 93,259评论 0 211
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 40,730评论 0 173
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 48,426评论 1 252
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 38,606评论 1 170
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 30,277评论 2 267
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 29,066评论 0 163
  • 想象着我的养父在大火中拼命挣扎,窒息,最后皮肤化为焦炭。我心中就已经是抑制不住地欢快,这就叫做以其人之道,还治其人...
    爱写小说的胖达阅读 28,821评论 6 227
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 32,410评论 0 212
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 29,180评论 2 213
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 30,498评论 1 223
  • 白月光回国,霸总把我这个替身辞退。还一脸阴沉的警告我。[不要出现在思思面前, 不然我有一百种方法让你生不如死。]我...
    爱写小说的胖达阅读 24,162评论 0 31
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 27,035评论 2 211
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 31,412评论 3 201
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 25,586评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 25,933评论 0 163
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 33,370评论 2 228
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 33,487评论 2 229

推荐阅读更多精彩内容

  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 133,996评论 18 139
  • 博客原文 翻译作品,水平有限,如有错误,烦请留言指正。原文请见 官网英文文档 引言 概述 Apache Flume...
    rabbitGYK阅读 11,355评论 13 34
  • 介绍 概述 Apache Flume是为有效收集聚合和移动大量来自不同源到中心数据存储而设计的可分布,可靠的,可用...
    ximengchj阅读 3,429评论 0 13
  • 介绍 概述 Apache Flume是一个分布式的,可靠的,高可用的系统,用于高效地从多个不同的数据源收集,汇总及...
    steanxy阅读 987评论 0 1
  • 名字里有月,网名是小太阳,但是我却深深的爱上了星星。 曾经渴望自己活成太阳的样子,越开心就越嗨,将温暖带去...
    大太阳咪咪笑阅读 105评论 0 0