ZK节点数过大导致不可用,引发ResourceManager挂掉

ZK节点数过大导致不可用,引发ResourceManager挂掉

故障经过

晚上8点多突然发现flink任务大面积挂掉重启的告警,然后打开 yarn-ui进行查看发现 ui也挂了
在这里插入图片描述
根据情况以及日志,初步判定RM挂了,然后查看RM 日志,发现ZK连不上,怀疑ZK有问题, 然后又登录ZK集群,查看ZK日志

##ZK日志
在这里插入图片描述
为了尽快恢复故障,减少故障时间,决定重启RM,但是启动失败,感觉RM启动HANG住了,仍然不可用,日志如下

在这里插入图片描述
发现ZK链不上,那回头看ZK,首先也是开启了重启大发,将ZK重启了一下,根据日志发现ZK正常启动,但是 仍然发现RM链不上ZK,
这时候开始手动执行zk-client去链接,链接是正常的,然后神奇的事情发生了,执行ls命令时,直接OOM异常。。。
卧槽,这到底时为什么,一脸懵逼,不过问题大概就在这了,内存不够,就先加内存起来再说,直接改ZK启动内存,然后重启
然后再用zk-client链接,再执行ls命令,OK 正常了,狂喜,以为这下搞定了
然后去重启RM,悲剧发生了,RM一直卡在那里,也不报错,就是起不来~~~
他到底在干嘛呢???为了搞清楚这个问题,我们开始jstack RM,然后发现了这个
在这里插入图片描述
他卡在了,加载RMState, 到底这个东西有多大,我们查看了集群配置RMState 是 存放在 zk 中的,我们又看了一下zk的监控,然后惊呆了,ZK的节点总数80万个,,,大部分都是RMSTATE下的。。。
现在终于搞明白,他为什么卡住起来不了。如果等他加载完毕,估计几个小时又过去了,为了快速恢复我们改为启动不加载,修改集群配置
yarn.resourcemanager.recovery.enabled: false
然后将RMSTATE从存储在ZK上改为存储在HDFS上,修改配置
yarn.resourcemanager.store.class
org.apache.hadoop.yarn.server.resourcemanager.recovery.ZKRMStateStore(原来配置)org.apache.hadoop.yarn.server.resourcemanager.recovery.FileSystemRMStateStore(修改后的配置)
再追加一个新配置
yarn.resourcemanager.fs.state-store.uri: /yarn/system/rmstor
然后重新RM, 集群恢复正常,
最后为了ZK的稳定性清理ZK中的大量RMSTATE数据,问题虽然解决了,但是ZK中的80万的节点是怎么来的?正常情况下一个任务下的RMSTATE文件数量也就几个,整个集群也就1000多个任务,一般也就几千个,到底是什么导致他出现了80万个?

排查文件过多的原因

我们把文件列表拉出来看了一下,有个别任务下的attempt文件非常多,这些文件是任务启动失败,然后重试之后所产生的文件,但是理论上我们已经配置了最大重试次数,为了确认,我们又去查看了一下文件,结果是
yarn.application-attempts = 10
那么为什么这个参数设置了之后并没有生效呢?他失败之后一直重启了几万次,导致生成了数万个attempts文件

我们用的是flink1.7, 对于1.7版本 设置akka timeout 时间作为这个窗口时间 默认为30s 在30s之内如果重启次数没达到max attempt 就会开启新一轮重启
在这里插入图片描述
flink 1.9版本的这个加入了yarn.application-attempt-failures-validity-interval 配置

PR链接:https://github.com/apache/flink/pull/8400

这个配置定义了一个错误次数累计的窗口 如果在此窗口内错误次数没有达到application-attempts 那么就会重启

public static final ConfigOption<Long> APPLICATION_ATTEMPT_FAILURE_VALIDITY_INTERVAL =
   key("yarn.application-attempt-failures-validity-interval")
   .defaultValue(10000L)
   .withDescription(Description.builder()
      .text("Time window in milliseconds which defines the number of application attempt failures when restarting the AM. " +
         "Failures which fall outside of this window are not being considered. " +
         "Set this value to -1 in order to count globally. " +
         "See %s for more information.", link("https://hortonworks.com/blog/apache-hadoop-yarn-hdp-2-2-fault-tolerance-features-long-running-services/", "here"))
      .build());

再看一下 yarn逻辑

private int getNumFailedAppAttempts() {
  int completedAttempts = 0;
  long endTime = this.systemClock.getTime();
  // Do not count AM preemption, hardware failures or NM resync
  // as attempt failure.
  for (RMAppAttempt attempt : attempts.values()) {
    if (attempt.shouldCountTowardsMaxAttemptRetry()) {
      if (this.attemptFailuresValidityInterval <= 0
          || (attempt.getFinishTime() > endTime
              - this.attemptFailuresValidityInterval)) {
        completedAttempts++;
      }
    }
  }
  return completedAttempts;
}

解决办法

flink1.7 版本

可以增加akka timeout时间窗口 来统计累计attempt重启次数  但是这种修改会影响全局 目前没有太好的办法

flink1.9 将 yarn.application-attempt-failures-validity-interval 设置为-1 进行全局累加

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值