記一次線上kafka一直rebalance故障

今天我司線上kafka消息代理出現(xiàn)錯誤日志,異常rebalance安吁,而且平均間隔2到3分鐘就會rebalance一次未辆,分析日志發(fā)現(xiàn)比較嚴重芹壕。錯誤日志如下

08-09 11:01:11 131 pool-7-thread-3 ERROR [] - 
commit failed 
org.apache.kafka.clients.consumer.CommitFailedException: Commit cannot be completed since the group has already rebalanced and assigned the partitions to another member. This means that the time between subsequent calls to poll() was longer than the configured max.poll.interval.ms, which typically implies that the poll loop is spending too much time message processing. You can address this either by increasing the session timeout or by reducing the maximum size of batches returned in poll() with max.poll.records.
        at org.apache.kafka.clients.consumer.internals.ConsumerCoordinator.sendOffsetCommitRequest(ConsumerCoordinator.java:713) ~[MsgAgent-jar-with-dependencies.jar:na]
        at org.apache.kafka.clients.consumer.internals.ConsumerCoordinator.commitOffsetsSync(ConsumerCoordinator.java:596) ~[MsgAgent-jar-with-dependencies.jar:na]
        at org.apache.kafka.clients.consumer.KafkaConsumer.commitSync(KafkaConsumer.java:1218) ~[MsgAgent-jar-with-dependencies.jar:na]
        at com.today.eventbus.common.MsgConsumer.run(MsgConsumer.java:121) ~[MsgAgent-jar-with-dependencies.jar:na]
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) [na:1.8.0_161]
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) [na:1.8.0_161]
        at java.lang.Thread.run(Thread.java:748) [na:1.8.0_161]

這個錯誤的意思是汇四,消費者在處理完一批poll的消息后,在同步提交偏移量給broker時報的錯踢涌。初步分析日志是由于當前消費者線程消費的分區(qū)已經(jīng)被broker給回收了通孽,因為kafka認為這個消費者死了,那么為什么呢睁壁?

分析問題

這里就涉及到問題是消費者在創(chuàng)建時會有一個屬性max.poll.interval.ms背苦,
該屬性意思為kafka消費者在每一輪poll()調(diào)用之間的最大延遲,消費者在獲取更多記錄之前可以空閑的時間量的上限互捌。如果此超時時間期滿之前poll()沒有被再次調(diào)用,則消費者被視為失敗行剂,并且分組將重新平衡秕噪,以便將分區(qū)重新分配給別的成員。

image.png

如上圖厚宰,在while循環(huán)里腌巾,我們會循環(huán)調(diào)用poll拉取broker中的最新消息。每次拉取后固阁,會有一段處理時長壤躲,處理完成后,會進行下一輪poll备燃。引入該配置的用途是,限制兩次poll之間的間隔凌唬,消息處理邏輯太重并齐,每一條消息處理時間較長,但是在這次poll()到下一輪poll()時間不能超過該配置間隔客税,協(xié)調(diào)器會明確地讓使用者離開組况褪,并觸發(fā)新一輪的再平衡。
max.poll.interval.ms默認間隔時間為300s

分析日志

從日志中我們能看到poll量有時能夠達到250多條


image.png

一次性拉取250多條消息進行消費更耻,而由于每一條消息都有一定的處理邏輯测垛,根據(jù)以往的日志分析,每條消息平均在500ms內(nèi)就能處理完成秧均。然而食侮,我們今天查到有兩條消息處理時間超過了1分鐘。

消息處理日志1

08-09 08:50:05 430 pool-7-thread-3 INFO [] - [RestKafkaConsumer] receive message (收到消息目胡,準備過濾锯七,然后處理), topic: member_1.0.0_event ,partition: 0 ,offset: 1504617
08-09 08:50:05 431 pool-7-thread-3 INFO [] - [RestKafkaConsumer]:解析消息成功,準備請求調(diào)用!
08-09 08:51:05 801 pool-7-thread-3 INFO [] - [HttpClient]:response code: {"status":200,"data":{"goodsSendRes":{"status":400,"info":"指>定商品送沒有可用的營銷活動--老pos機"},"fullAmountSendRes":{"status":400,"info":"滿額送沒有可用的營銷活動--老pos機"}},"info":"發(fā)券流程執(zhí)
行成功"}, event:com.today.api.member.events.ConsumeFullEvent, url:https://wechat-lite.today36524.com/api/dapeng/subscribe/index,event內(nèi)
容:{"id":36305914,"score":16,"orderPrice":15.9,"payTime":1533775401000,"thirdTransId":"4200000160201808

消息處理日志2

08-09 08:51:32 450 pool-7-thread-3 INFO [] - [RestKafkaConsumer] receive message (收到消息,準備過濾誉己,然后處理), topic: member_1.0.0_event ,partition: 0 ,offset: 1504674
08-09 08:51:32 450 pool-7-thread-3 INFO [] - [RestKafkaConsumer]:解析消息成功,準備請求調(diào)用!
08-09 08:52:32 843 pool-7-thread-3 INFO [] - [HttpClient]:response code: {"status":200,"data":{"goodsSendRes":{"status":400,"info":"指>定商品送沒有可用的營銷活動--老pos機"},"fullAmountSendRes":{"status":400,"info":"滿額送沒有可用的營銷活動--老pos機"}},"info":"發(fā)券流程執(zhí)
行成功"}, event:com.today.api.member.events.ConsumeFullEvent, url:https://wechat-lite.today36524.com/api/dapeng/subscribe/index,event內(nèi)
容:{"id":36306061,"score":3,"orderPrice":3.0,"payTime":1533775482000,"thirdTransId":"420000016320180809

我們看到消息消費時間都超過了1分鐘眉尸。

分析原因

如下是我們消費者處理邏輯(省略部分代碼)

 while (isRunning) {
            ConsumerRecords<KEY, VALUE> records = consumer.poll(100);
            if (records != null && records.count() > 0) {
           
            for (ConsumerRecord<KEY, VALUE> record : records) {
                dealMessage(bizConsumer, record.value());
                try {
                    //records記錄全部完成后,才提交
                      consumer.commitSync();
                } catch (CommitFailedException e) {
                      logger.error("commit failed,will break this for loop", e);
                        break;
                }
            }
}

poll()方法該方法輪詢返回消息集巨双,調(diào)用一次可以獲取一批消息噪猾。

kafkaConsumer調(diào)用一次輪詢方法只是拉取一次消息≈郏客戶端為了不斷拉取消息袱蜡,會用一個外部循環(huán)不斷調(diào)用消費者的輪詢方法。每次輪詢到消息疼阔,在處理完這一批消息后戒劫,才會繼續(xù)下一次輪詢半夷。但如果一次輪詢返回的結(jié)構(gòu)沒辦法及時處理完成,會有什么后果呢迅细?服務(wù)端約定了和客戶端max.poll.interval.ms巫橄,兩次poll最大間隔。如果客戶端處理一批消息花費的時間超過了這個限制時間茵典,服務(wù)端可能就會把消費者客戶端移除掉湘换,并觸發(fā)rebalance

拉取偏移量與提交偏移量

kafka的偏移量(offset)是由消費者進行管理的统阿,偏移量有兩種彩倚,拉取偏移量(position)與提交偏移量(committed)。拉取偏移量代表當前消費者分區(qū)消費進度扶平。每次消息消費后帆离,需要提交偏移量。在提交偏移量時结澄,kafka會使用拉取偏移量的值作為分區(qū)的提交偏移量發(fā)送給協(xié)調(diào)者哥谷。
如果沒有提交偏移量,下一次消費者重新與broker連接后麻献,會從當前消費者group已提交到broker的偏移量處開始消費们妥。
所以,問題就在這里勉吻,當我們處理消息時間太長時,已經(jīng)被broker剔除监婶,提交偏移量又會報錯。所以拉取偏移量沒有提交到broker齿桃,分區(qū)又rebalance惑惶。下一次重新分配分區(qū)時,消費者會從最新的已提交偏移量處開始消費源譬。這里就出現(xiàn)了重復消費的問題集惋。

解決方案

1.增加max.poll.interval.ms處理時長

kafka消費者 默認此間隔時長為300s,本次故障是300s都沒處理完成踩娘,于是改成500s刮刑。

max.poll.interval.ms=500000

2.設(shè)置分區(qū)拉取閾值

kafkaConsumer調(diào)用一次輪詢方法只是拉取一次消息⊙剩客戶端為了不斷拉取消息雷绢,會用一個外部循環(huán)不斷調(diào)用輪詢方法poll()。每次輪詢后理卑,在處理完這一批消息后翘紊,才會繼續(xù)下一次的輪詢。

max.poll.records = 50

3.poll到的消息藐唠,處理完一條就提交一條帆疟,當出現(xiàn)提交失敗時鹉究,馬上跳出循環(huán),這時候kafka就會進行rebalance,下一次會繼續(xù)從當前offset進行消費踪宠。

 while (isRunning) {
            ConsumerRecords<KEY, VALUE> records = consumer.poll(100);
            if (records != null && records.count() > 0) {
           
            for (ConsumerRecord<KEY, VALUE> record : records) {
                dealMessage(bizConsumer, record.value());
                try {
                    //records記錄全部完成后自赔,才提交
                      consumer.commitSync();
                } catch (CommitFailedException e) {
                      logger.error("commit failed,will break this for loop", e);
                        break;
                }
            }
}

附錄 查詢?nèi)罩?某個topic的 partition 的rebalance過程

member_1分區(qū)

時間 revoked position revoked committed 時間 assigned
08:53:21 1508667 1508509 08:57:17 1508509
09:16:31 1509187 1508509 09:21:02 1508509
09:23:18 1509323 1508509 09:26:02 1508509
09:35:16 1508509 1508509 09:36:03 1508509
09:36:21 1508509 1508509 09:41:03 1508509
09:42:15 1509323 1508509 09:46:03 1508509
09:47:19 1508509 1508509 09:51:03 1508509
09:55:04 1509323 1509323 09:56:03 1509323
多余消費 被回滾 重復消費 10:01:03 1509323
10:02:20 1510205 1509323 10:06:03 1509323
10:07:29 1509323 1509323 10:08:35 1509323
10:24:43 1509693 1509693 10:25:18 1509693
10:28:38 1510604 1510604 10:35:18 1510604
10:36:37 1511556 1510604 10:40:18 1510604
10:54:26 1511592 1511592 10:54:32 1511592
- - - 10:59:32 1511979
11:01:11 1512178 1512178 11:03:40 1512178
11:04:35 1512245 1512245 11:08:49 1512245
11:12:47 1512407 1512407 11:12:49 1512407
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市柳琢,隨后出現(xiàn)的幾起案子绍妨,更是在濱河造成了極大的恐慌,老刑警劉巖柬脸,帶你破解...
    沈念sama閱讀 217,734評論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件他去,死亡現(xiàn)場離奇詭異,居然都是意外死亡倒堕,警方通過查閱死者的電腦和手機灾测,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,931評論 3 394
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來涩馆,“玉大人行施,你說我怎么就攤上這事』昴牵” “怎么了?”我有些...
    開封第一講書人閱讀 164,133評論 0 354
  • 文/不壞的土叔 我叫張陵稠项,是天一觀的道長涯雅。 經(jīng)常有香客問我,道長展运,這世上最難降的妖魔是什么活逆? 我笑而不...
    開封第一講書人閱讀 58,532評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮拗胜,結(jié)果婚禮上蔗候,老公的妹妹穿的比我還像新娘。我一直安慰自己埂软,他們只是感情好锈遥,可當我...
    茶點故事閱讀 67,585評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著勘畔,像睡著了一般所灸。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上炫七,一...
    開封第一講書人閱讀 51,462評論 1 302
  • 那天爬立,我揣著相機與錄音,去河邊找鬼万哪。 笑死侠驯,一個胖子當著我的面吹牛抡秆,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播吟策,決...
    沈念sama閱讀 40,262評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼儒士,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了踊挠?” 一聲冷哼從身側(cè)響起乍桂,我...
    開封第一講書人閱讀 39,153評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎效床,沒想到半個月后睹酌,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,587評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡剩檀,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,792評論 3 336
  • 正文 我和宋清朗相戀三年憋沿,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片沪猴。...
    茶點故事閱讀 39,919評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡辐啄,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出运嗜,到底是詐尸還是另有隱情壶辜,我是刑警寧澤,帶...
    沈念sama閱讀 35,635評論 5 345
  • 正文 年R本政府宣布担租,位于F島的核電站砸民,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏奋救。R本人自食惡果不足惜岭参,卻給世界環(huán)境...
    茶點故事閱讀 41,237評論 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望尝艘。 院中可真熱鬧演侯,春花似錦、人聲如沸背亥。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,855評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽隘梨。三九已至程癌,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間轴猎,已是汗流浹背嵌莉。 一陣腳步聲響...
    開封第一講書人閱讀 32,983評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留捻脖,地道東北人锐峭。 一個月前我還...
    沈念sama閱讀 48,048評論 3 370
  • 正文 我出身青樓中鼠,卻偏偏與公主長得像,于是被迫代替她去往敵國和親沿癞。 傳聞我的和親對象是個殘疾皇子援雇,可洞房花燭夜當晚...
    茶點故事閱讀 44,864評論 2 354

推薦閱讀更多精彩內(nèi)容