最美情侣中文字幕电影,在线麻豆精品传媒,在线网站高清黄,久久黄色视频

歡迎光臨散文網(wǎng) 會員登陸 & 注冊

萬字長文:手把手教你實(shí)現(xiàn)一套高效的IM長連接自適應(yīng)心跳?;顧C(jī)制

2022-05-18 15:59 作者:nickkckckck  | 我要投稿

本文作者“Carson”,現(xiàn)就職于騰訊公司,原題“高效?;铋L連接:手把手教你實(shí)現(xiàn)自適應(yīng)的心跳保活機(jī)制”,有較多修訂和改動。

1、引言

當(dāng)要實(shí)現(xiàn)IM即時通訊聊天、消息推送等高實(shí)時性需求時,我們一般會選擇長連接的通信方式。

而真正當(dāng)實(shí)現(xiàn)長連接方式時,會遇到很多技術(shù)問題,比如最常見的長連接保活問題。

今天,我將通過本篇文章,手把手教大家實(shí)現(xiàn)一套可自適應(yīng)的心跳?;顧C(jī)制,從而能高效穩(wěn)定地維持諸如IM聊天這類需求的長連接。

?

學(xué)習(xí)交流:

- 移動端IM開發(fā)入門文章:《新手入門一篇就夠:從零開發(fā)移動端IM》

- 開源IM框架源碼:https://github.com/JackJiang2011/MobileIMSDK?

(本文同步發(fā)布于:http://www.52im.net/thread-3908-1-1.html)

2、相關(guān)文章

  1. 《為何基于TCP協(xié)議的移動端IM仍然需要心跳保活機(jī)制?》

  2. 《一文讀懂即時通訊應(yīng)用中的網(wǎng)絡(luò)心跳包機(jī)制:作用、原理、實(shí)現(xiàn)思路等》

  3. 《一種Android端IM智能心跳算法的設(shè)計與實(shí)現(xiàn)探討(含樣例代碼)》

  4. 《自已開發(fā)IM有那么難嗎?手把手教你自擼一個Andriod版簡易IM (有源碼)》

  5. 《跟著源碼學(xué)IM(一):手把手教你用Netty實(shí)現(xiàn)心跳機(jī)制、斷線重連機(jī)制》

  6. 《跟著源碼學(xué)IM(五):正確理解IM長連接、心跳及重連機(jī)制,并動手實(shí)現(xiàn)》

3、什么是長連接

認(rèn)識長連接:

長連接的主要作是通過長時間保持雙方連接,從而:

  • 1)提高通信速度;

  • 2)確保實(shí)時性;

  • 3)避免短時間內(nèi)重復(fù)連接所造成的信道資源和網(wǎng)絡(luò)資源的浪費(fèi)。

長連接與短連接的區(qū)別:

PS:對于IM這類的開發(fā)者而言,通常大家都把HTTP協(xié)議稱“短連接”、把直接基于TCP、UDP或WebSocket的socket稱為“長連接”。

4、導(dǎo)致長連接斷開的原因

4.1 基本概念

從上節(jié)可知,在使用長連接的情況下,雙方的所有通信都建立在1條長連接上(比如1次TCP連接)。所以,長連接需要持續(xù)保持雙方連接才可使得雙方持續(xù)通信。

然而,實(shí)際情況是,長連接會存在斷開的情況。

這些斷開原因主要是:

  • 1)長連接所在進(jìn)程被殺死(這主要說的是移動端);

  • 2)NAT超時;

  • 3)網(wǎng)絡(luò)狀態(tài)發(fā)生變化;

  • 4)其他不可抗因素(網(wǎng)絡(luò)狀態(tài)差、DHCP的租期等等 )。

下面,我將對每種原因進(jìn)行分析。

4.2 具體分析

1)原因1:進(jìn)程被殺死

當(dāng)進(jìn)程被殺死后,長連接也會隨之?dāng)嚅_。進(jìn)程被殺在Andriod端是最常見的問題,限于篇幅就不在此展開這個話題,有興趣可以閱讀這篇:《Android P正式版即將到來:后臺應(yīng)用?;睢⑾⑼扑偷恼嬲瑝簟?。

2)原因2:NAT 超時(重點(diǎn)關(guān)注)

NAT超時現(xiàn)象如下:

?

各運(yùn)營商和地區(qū)的NAT超時時間如下:

PS:上述數(shù)據(jù)來源于微信團(tuán)隊(duì)的《移動端IM實(shí)踐:實(shí)現(xiàn)Android版微信的智能心跳機(jī)制》一文,隨著4G、5G的普及,這些數(shù)據(jù)有可能已發(fā)生變化,請以實(shí)際測試結(jié)果為準(zhǔn)。

特別注意:排除其他外因(網(wǎng)絡(luò)切換、NAT超時、人為原因),TCP長連接在雙方都不斷開連接的情況上,本質(zhì)上是不會自動中斷的(也就是不需要心跳包來維持,可以驗(yàn)證一下:讓2臺電腦連上同1個Wifi,其中1臺做服務(wù)器, 另1臺做客戶端連接服務(wù)器(無設(shè)置KeepAlive)。只要電腦、路由器不斷網(wǎng)斷電,那么,2臺電腦的長連接是不會自動中斷的)。

Jack Jiang注:上述論述可能不太準(zhǔn)確,有新興趣的讀者可以詳讀《拔掉網(wǎng)線再插上,TCP連接還在嗎?一文即懂!》。

3)原因3:網(wǎng)絡(luò)狀態(tài)發(fā)生變化

當(dāng)移動客戶端網(wǎng)絡(luò)狀態(tài)發(fā)生變化時(如移動網(wǎng)絡(luò) & Wifi切換、斷開、重連),也會使長連接斷開。

4)原因4:其他不可抗因素

如網(wǎng)絡(luò)狀態(tài)差、DHCP的租期到期等等,都會使得長連接發(fā)生 偶然的斷開。DHCP的租期到期:對于 Android系統(tǒng), DHCP到了租期后不會主動續(xù)約(繼續(xù)使用過期IP),從而導(dǎo)致長連接斷開。

5、高效維持長連接的解決方案

5.1 基本介紹

在了解長連接斷開原因后,針對這些原因,此處給出我的高效維持長連接的解決方案(如下圖所示)。

為此,若需有效維持長連接,則需要做到:

說得簡單點(diǎn),高效維持長連接的關(guān)鍵在于:

  • 1)?;睿禾幱谶B接狀態(tài)時要做到盡量不要斷;

  • 2)重連:連接斷了之后要能繼續(xù)重連回來。

5.2 具體措施

1)措施1:進(jìn)程保活

整體概括如下:

PS:關(guān)于Android的進(jìn)程?;睿@個話題就很熱門了,感興趣可以順著下面的文章詳細(xì)讀一讀:

  1. 《應(yīng)用?;罱K極總結(jié)(一):Android6.0以下的雙進(jìn)程守護(hù)?;顚?shí)踐》

  2. 《應(yīng)用?;罱K極總結(jié)(二):Android6.0及以上的保活實(shí)踐(進(jìn)程防殺篇)》

  3. 《應(yīng)用?;罱K極總結(jié)(三):Android6.0及以上的?;顚?shí)踐(被殺復(fù)活篇)》

  4. 《Android進(jìn)程?;钤斀猓阂黄恼陆鉀Q你的所有疑問》

  5. 《微信團(tuán)隊(duì)原創(chuàng)分享:Android版微信后臺?;顚?shí)戰(zhàn)分享(進(jìn)程?;钇?》

  6. 《Android P正式版即將到來:后臺應(yīng)用?;睢⑾⑼扑偷恼嬲瑝簟?/p>

  7. 《全面盤點(diǎn)當(dāng)前Android后臺?;罘桨傅恼鎸?shí)運(yùn)行效果(截止2019年前)》

  8. 《2020年了,Android后臺?;钸€有戲嗎?看我如何優(yōu)雅的實(shí)現(xiàn)!》

  9. 《史上最強(qiáng)Android保活思路:深入剖析騰訊TIM的進(jìn)程永生技術(shù)》

  10. 《Android進(jìn)程永生技術(shù)終極揭密:進(jìn)程被殺底層原理、APP應(yīng)對被殺技巧》

  11. 《Android?;顝娜腴T到放棄:乖乖引導(dǎo)用戶加白名單吧(附7大機(jī)型加白示例)》

2)措施2:心跳?;顧C(jī)制

這是本文的重點(diǎn),下節(jié)開始會詳細(xì)解析

3)措施3:斷線重連機(jī)制

原理就是:檢測網(wǎng)絡(luò)狀態(tài)變化并及時判斷連接的有效性。

具體實(shí)現(xiàn):這個其實(shí)跟心跳?;顧C(jī)制是一套完整的邏輯,所以下面會在心跳?;顧C(jī)制中一起講解。

6、心跳?;顧C(jī)制簡介

心跳?;顧C(jī)制的整體介紹如下:

不過,很多人容易混淆把心跳機(jī)制和傳統(tǒng)的HTTP輪詢機(jī)制搞混。

下面給出二者區(qū)別:

7、主流IM的心跳機(jī)制分析和對比

對國、內(nèi)外主流的移動IM產(chǎn)品(WhatsAPP、Line、微信)進(jìn)行了心跳機(jī)制的簡單分析和對比。

具體請看下圖:

PS:以上數(shù)據(jù)來自于微信團(tuán)隊(duì)分享的《移動端IM實(shí)踐:WhatsAPP、Line、微信的心跳策略分析》一文。

8、心跳?;顧C(jī)制方案總體設(shè)計

下面,我將根據(jù)市面上主流的心跳機(jī)制,設(shè)計了一套心跳機(jī)制方案。

心跳機(jī)制方案的基本流程:

?

對于心跳機(jī)制方案設(shè)計的主要考慮因素是:

  • 1)要保證消息的實(shí)時性;

  • 2)要考慮耗費(fèi)設(shè)備的資源(網(wǎng)絡(luò)流量、電量、CPU等等)。

從上圖可以看出,對于心跳機(jī)制方案設(shè)計的要點(diǎn)在于:

  • 1)心跳包的規(guī)格(內(nèi)容 & 大?。?;

  • 2)心跳發(fā)送的間隔時間;

  • 3)斷線重連機(jī)制 (核心 = 如何 判斷長連接的有效性)。

在下面的方案設(shè)計中,將針對這3個問題給出詳細(xì)的解決方案。

9、心跳機(jī)制方案的詳細(xì)設(shè)計

9.1 心跳包的規(guī)格

為了減少流量并提高發(fā)送效率,需要精簡心跳包的設(shè)計。

主要從心跳包的內(nèi)容和大小入手,設(shè)計原則具體如下:

設(shè)計方案:

心跳包 = 1個攜帶少量信息 & 大小在10字節(jié)內(nèi)的信息包

9.2 心跳發(fā)送的間隔時間

為了 防止NAT超時并減少設(shè)備資源的消耗(網(wǎng)絡(luò)流量、電量、CPU等等),心跳發(fā)送的間隔時間是整個心跳機(jī)制方案設(shè)計的重點(diǎn)。

心跳發(fā)送間隔時間的設(shè)計原則如下:

?

9.3 最常用的心跳間隔方案

一般,最直接且常用的心跳發(fā)送間隔時間設(shè)置方案多采用:“每隔估計 x 分鐘發(fā)送心跳包1次”。其中,x <5分鐘即可(綜合主流移動IM產(chǎn)品,此處建議 x= 4分鐘)。

但是,這種方案存在一些問題:

PS:關(guān)于固定心跳間隔的方案具體實(shí)現(xiàn),可以詳細(xì)參考:

  1. 《跟著源碼學(xué)IM(一):手把手教你用Netty實(shí)現(xiàn)心跳機(jī)制、斷線重連機(jī)制》;

  2. 《跟著源碼學(xué)IM(五):正確理解IM長連接、心跳及重連機(jī)制,并動手實(shí)現(xiàn)》;

  3. 《自已開發(fā)IM有那么難嗎?手把手教你自擼一個Andriod版簡易IM (有源碼)》。

9.4 自適應(yīng)心跳間隔方案

下面,我將詳細(xì)講解自適應(yīng)心跳間隔時間的設(shè)計方案。

基本邏輯:

?

該方案需要解決的有2個核心問題。

1)如何自適應(yīng)計算心跳間隔 從而使得心跳間隔 接近 當(dāng)前NAT 超時時間?

答:不斷增加心跳間隔時間進(jìn)行心跳應(yīng)答測試,直到心跳失敗5次后,即可找出最接近 當(dāng)前NAT 超時時間的心跳間隔時間。

具體請看下圖:

注:只有當(dāng)心跳間隔 接近 NAT 超時時間 時,才能最大化平衡 長連接不中斷 & 設(shè)備資源消耗最低的問題。

2)如何檢測 當(dāng)前網(wǎng)絡(luò)環(huán)境的NAT 超時時間 發(fā)生了變化 ?

答:當(dāng)前發(fā)送心跳包成功 的最大間隔時間(即最接近NAT超時時間的心跳間隔) 發(fā)送失敗5次后,則判斷當(dāng)前網(wǎng)絡(luò)環(huán)境的NAT 超時時間 發(fā)生了變化。

具體請看下圖:

注:在檢測到 NAT 超時時間 發(fā)生變化后,重新自適應(yīng)計算心跳間隔 從而使得心跳間隔 接近 NAT 超時時間

總結(jié)一下:統(tǒng)籌以上2個核心問題,總結(jié)出自適應(yīng)心跳間隔時間設(shè)計方案為下圖:

PS:關(guān)于自適應(yīng)心跳機(jī)制的設(shè)計和實(shí)現(xiàn),可以詳細(xì)參考:

  1. 《移動端IM實(shí)踐:實(shí)現(xiàn)Android版微信的智能心跳機(jī)制》;

  2. 《一種Android端IM智能心跳算法的設(shè)計與實(shí)現(xiàn)探討(含樣例代碼)》。

10、斷線重連機(jī)制的實(shí)現(xiàn)

技術(shù)上來說:長連接的心跳?;钜蕾囉谛奶鴻C(jī)制,在心跳機(jī)制起作用的情況下,適時啟動斷線重連機(jī)制,在心跳機(jī)制和斷線重連機(jī)制的共同作用下才能實(shí)現(xiàn)真正的心跳?;睢5珵榱俗屵壿嫺逦?,我把斷線重連機(jī)制跟心跳機(jī)制單獨(dú)各作為一節(jié)來講解。本節(jié)講的是斷片線重連機(jī)制。

該機(jī)制的核心在于:如何判斷長連接的有效性。即:什么情況下視為長連接斷線?

1)設(shè)計原則:

基本邏輯就是:判斷長連接是否有效的準(zhǔn)則 = 服務(wù)器是否返回心跳應(yīng)答。

此處需要分清長連接的“存活 & 有效“狀態(tài)的區(qū)別:

?

2)具體方案:

實(shí)現(xiàn)思路:通過計數(shù)計算,若連續(xù)5次發(fā)送心跳后,服務(wù)器都無心跳應(yīng)答,則視為長連接無效。

判斷流程:

3)網(wǎng)上流傳的方案:

在網(wǎng)上流傳著一些用于判斷長連接是否有效的方案,具體介紹如下:?

至此,關(guān)于心跳?;顧C(jī)制已經(jīng)講解完畢。

11、方案小結(jié)

有必要總結(jié)一下我在上兩節(jié)分享的心跳機(jī)制和斷線重連機(jī)制,這兩個機(jī)制組成了本文的長連接心跳?;钔暾壿?。

設(shè)計方案:?

流程設(shè)計:

注:標(biāo)識 “灰色” 的判斷流程參考上文描述。

12、進(jìn)一步優(yōu)化和完善心跳?;罘桨?/h1>

12.1 基本情況

上兩節(jié)中的方案依然會存在技術(shù)缺陷,從而導(dǎo)致長連接斷開(比如:長連接本身不可用(此時重連多少次也沒用))。

下面將優(yōu)化和完善上述方案,從而保證 客戶端與服務(wù)器依然保持著通信狀態(tài)。

優(yōu)化點(diǎn)主要是:

  • 1)確保當(dāng)前網(wǎng)絡(luò)的有效性和穩(wěn)定性再開始長連接;

  • 2)自適應(yīng)計算心跳包間隔時間的時機(jī)。

12.2 確保網(wǎng)絡(luò)的有效性和穩(wěn)定性后再開始長連接

問題描述:

?

解決方案:

加入到原有的心跳保活機(jī)制主流程:

12.3 自適應(yīng)計算心跳包間隔時間的時機(jī)

問題描述:

?

方案設(shè)計:

?

加入到到原有的心跳?;顧C(jī)制主流程:

?

12.4 小結(jié)一下

13、額外思考:TCP協(xié)議自帶的KeepAlive機(jī)制能否替代心跳機(jī)制?

很多人認(rèn)為,TCP 協(xié)議自身就有KeepAlive機(jī)制,為何基于它的通訊鏈接,仍需在應(yīng)用層實(shí)現(xiàn)額外的心跳保活機(jī)制?

  • 結(jié)論是:無法替代;

  • 原因是:TCP KeepAlive機(jī)制的作用是檢測連接的有無(死活),但無法檢測連接是否有效。

注:“連接有效”的定義 = 雙方具備發(fā)送 & 接收消息的能力。

先來看看KeepAlive 機(jī)制是什么:

?

KeepAlive 的機(jī)制不可替代心跳機(jī)制的具體原因如下:

?

特別注意:

  • 1)KeepAlive 機(jī)制只是操作系統(tǒng)底層的一個被動機(jī)制,不應(yīng)該被上層應(yīng)用層使用;

  • 2)當(dāng)系統(tǒng)關(guān)閉一個由KeepAlive 機(jī)制檢查出來的死連接時,是不會主動通知上層應(yīng)用的,只能通過調(diào)用相應(yīng)IO操作的返回值中發(fā)現(xiàn)。

小結(jié)一下就是:KeepAlive機(jī)制無法代替心跳機(jī)制,需要在應(yīng)用層 自己實(shí)現(xiàn)心跳機(jī)制以檢測長連接的有效性,從而高效維持長連接。

Jack Jiang注:關(guān)于TCP本身的KeepAlive機(jī)制,可能詳讀:

  1. 《為何基于TCP協(xié)議的移動端IM仍然需要心跳?;顧C(jī)制?》

  2. 《徹底搞懂TCP協(xié)議層的KeepAlive?;顧C(jī)制》

14、本文總結(jié)

看完本文后,相信在高效維持長連接的需求下,你可以完美地解決了!

本文方案的主體設(shè)計就是:

方案的優(yōu)化和完善內(nèi)容就是:

15、參考資料

[1]?TCP/IP詳解 卷1:協(xié)議

[2]?為何基于TCP協(xié)議的移動端IM仍然需要心跳?;顧C(jī)制?

[3]?徹底搞懂TCP協(xié)議層的KeepAlive?;顧C(jī)制

[4]?萬字長文,一篇吃透WebSocket:概念、原理、易錯常識、動手實(shí)踐

[5]?移動端IM實(shí)踐:實(shí)現(xiàn)Android版微信的智能心跳機(jī)制

[6]?移動端IM實(shí)踐:WhatsAPP、Line、微信的心跳策略分析

[7]?微信團(tuán)隊(duì)原創(chuàng)分享:Android版微信后臺保活實(shí)戰(zhàn)分享(網(wǎng)絡(luò)?;钇?

[8]?融云技術(shù)分享:融云安卓端IM產(chǎn)品的網(wǎng)絡(luò)鏈路?;罴夹g(shù)實(shí)踐

[9]?阿里IM技術(shù)分享(五):閑魚億級IM消息系統(tǒng)的及時性優(yōu)化實(shí)踐

[10]?2020年了,Android后臺?;钸€有戲嗎?看我如何優(yōu)雅的實(shí)現(xiàn)!

(本文同步發(fā)布于:http://www.52im.net/thread-3908-1-1.html)


萬字長文:手把手教你實(shí)現(xiàn)一套高效的IM長連接自適應(yīng)心跳?;顧C(jī)制的評論 (共 條)

分享到微博請遵守國家法律
屏山县| 阿城市| 吉林市| 本溪| 建瓯市| 芒康县| 积石山| 百色市| 阳城县| 高雄市| 商河县| 香港 | 海宁市| 鄂尔多斯市| 惠东县| 宝应县| 巧家县| 金华市| 九江县| 桃园县| 岱山县| 探索| 固安县| 五常市| 青川县| 车险| 隆林| 辽宁省| 克什克腾旗| 庄浪县| 临沂市| 鄂州市| 博白县| 黎城县| 榆林市| 若羌县| 屏边| 霍林郭勒市| 孟州市| 徐州市| 舞钢市|