愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

本文原始內容由愛奇藝技術產品團隊原創分享,本次有修訂和改動。

1、引言

由於移動網絡的複雜性特點,編寫高質量、體驗好的具備網絡通信能力的移動端應用(尤其是即時通訊這類網絡質量高度敏感的應用)有很大的挑戰性。

我們平時看到的移動網絡主要有如下三個典型特點:

1)移動狀態網絡信號不穩定,高時延、易抖動丟包、通道狹窄;

2)移動狀態網絡接入類型和接入點變化頻繁;

3)移動狀態用戶使用高頻化、碎片化、非WIFI流量敏感。

(▲ 上述文字,引用自《移動端IM開發者必讀(一):通俗易懂,理解移動網絡的“弱”和“慢”》)

正是由於上述特點,移動端應用在進行網絡數據通信時會面臨各種複雜多變的問題。

無論後面的技術有多複雜,但對於普通用戶使用APP來說,能順暢的完成網絡請求,是理所當然的事。換句話說,APP網絡請求成功率,重要性直接體現在它能直接決定APP服務的可用性,直接影響到數據通信、視頻播放、廣告展現、支付便捷等服務質量。

本文將以愛奇藝的iOS端APP為例,分享對移動網絡請求成功率優化方面的技術實踐之路。

本文同時發佈於“即時通訊技術圈”公眾號。

(本文已同步發佈於:
http://www.52im.net/thread-2981-1-1.html)

2、相關文章

《現代移動端網絡短連接的優化手段總結:請求速度、弱網適應、安全保障》

《移動端IM開發者必讀(一):通俗易懂,理解移動網絡的“弱”和“慢”》(* 必讀好文)

《移動端IM開發者必讀(二):史上最全移動弱網絡優化方法總結》

《全面瞭解移動端DNS域名劫持等雜症:技術原理、問題根源、解決方案等》

《美圖App的移動端DNS優化實踐:HTTPS請求耗時減小近半》

《百度APP移動端網絡深度優化實踐分享(一):DNS優化篇》

《百度APP移動端網絡深度優化實踐分享(二):網絡連接優化篇》

《百度APP移動端網絡深度優化實踐分享(三):移動端弱網優化篇》

3、導致移動端網絡請求失敗的因素

想要優化移動端網絡請求成功率,先來了解移動端網絡請求全鏈條可能導致請求失敗的環節有哪些。

這些環節往往由以下兩類因素導致:

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

第一類:不可改善因素:

1)iOS系統對APP的網絡訪問權限控制、飛行模式或者無網絡連接。檢測和識別這三種情況,通過適當方式提示用戶;

2)路由器故障。

第二類:可以改善因素:

1)蜂窩/Wifi信號的強弱、連接擁堵的假連接狀態;

2)DNS故障(比如DNS劫持等);

3)運營商局部節點故障;

4)自有運營負載均衡故障;

5)業務服務器故障:HTTP響應錯誤,對應APM的HTTP響應錯誤率;

6)業務邏輯錯誤:監控子類解析結果,對應APM的解析錯誤率監控。

對於不可改善因素:目前只能通過網絡診斷識別出故障類型,引導用戶手動去授權訪問網絡或者連接可用網絡。

其中,如果是路由器故障,可以引導用戶重啟路由器或者切換4G。通過愛奇藝APP的數據監控,大致可以看到用戶無網連接的時長佔比有3.8%左右,這說明提供好的無網提示變得十分重要,而從用戶使用蜂窩信號的弱信號(0格和1格信號)時長佔比有9%左右時長,也可以看出移動端網絡環境的複雜性。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

針對可以改善的因素,解決方法可大致分為三類:

1)網絡層錯誤,對應因素1到4。主要體現為超時報錯;

2)HTTP響應錯誤,對應因素5。HTTP狀態碼為400及以上;

3)解析錯誤,對應因素6。由基線網絡庫定義的重載接口進行監控。

為了提高網絡請求成功率,首先需要建立監控體系,從而使得基線網絡庫能夠通過網絡統計模塊向APM投遞各種維度的網絡請求數據。有了APM的數據統計後,才能有效的發現導致端上網絡失敗的原因,進而解決問題。

除此之外,由於端上網絡請求數據巨大,存儲空間的限制使得APM只能採樣2%的用戶,因此針對重點業務的網絡請求(比如首頁)則進行了全量採集,從而對成功率的優化實現更客觀全面的評估。

4、在基線網絡庫這一層針對不同業務提供不同的補償思路

在優化之前,通過APM的歸類分析可以得出:請求失敗的主要報錯是超時(-1001)的佔比達到九成,與此同時SSL錯誤,DNS解析錯誤佔比緊隨其後。根據這一數據統計,重試成為最主要的請求成功率優化的措施。

經過不斷探索和實踐總結,基線網絡庫針對不同業務需求提供了四種不同的重試手段。

1)IP直連重試,通過配置直連IP數來控制重試次數:

Scheme不變,Host改為直接使用IP(消除域名解析風險)。由於此舉需要各個業務線自己提供直連的IP,目前接入的業務主要是登錄等強制要求HTTPS連接的業務。

2)超級管道重試,可以配置1~3次重試:

公司自研基於HTTP的網關代理服務(類似於遠程charles代理)。Host改為代理IP(消除域名解析風險),Scheme改為HTTP(消除SSL風險,h2降級為HTTP1.1)。由於該措施需要付出流量成本,目前接入的業務都是關鍵核心業務,比如首頁等。

3)HTTP重試,可以配置1~3次重試:

Scheme修改為HTTP(消除SSL風險,h2降級為HTTP1.1),其他不變。鑑於其為普惠性重試手段,目前接入非關鍵核心的一般業務。

4)原url重試,可以配置1~3次重試:

Scheme和host等都不變,通常意義上理解的重試,單純的再請求一次。此舉目前不是推薦重試手段,由業務方自主決定。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

除了單個重試手段可以重試多次,基礎網絡庫也支持多種重試手段的組合,四種重試手段的優先次序為:IP直連重試 > 超級管道重試 > HTTP重試 > 原URL重試。扣除無網情況,首頁推薦頁CARD接口成功率通過組合重試在2020第一季度末達到了99.76%。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

5、其它影響移動端網絡請求成功率的因素

除了重試,還有以下因素對網絡請求成功率有直接影響。

1)HTTP/2 vs HTTP/1.1:推薦的請求策略是首次請求走H2,當失敗重試時走HTTP/1.1:

HTTP/2對HTTP/1.1最大改進是共用一個TCP連接(詳見《從HTTP/0.9到HTTP/2:一文讀懂HTTP協議的歷史演變和設計思路》),其在網絡順暢時,為HTTP/2帶來了速度上的優勢。但當網絡變壞時,TCP包的絕對順序編號會導致一個包的丟失而堵住後面所有的請求。這樣單TCP連接反而擴大了擁堵,增大了請求失敗的可能性。

NSURLSession是HTTP協議自適應的,不能控制請求使用HTTP/2或者HTTP/1.1。不過由於業界事實上的標準要求HTTP/2必須是HTTPs的,這樣通過將URL Scheme改為HTTP可以間接降級到HTTP/1.1。

2)適當的超時設置是一個重要影響因素:

NSURLSession的超時實際上是TCP的包間超時,並不是整體請求耗時的超時。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

推薦的超時設置策略是:首次請求的超時可以小一點,而重試的超時應該大一些。

3)接口請求過於密集併發可能降低請求成功率:

比如播放記錄的upload接口在加上多次重試後,成功率仍然只有98.2%。APM監控此接口在IPv4環境失敗率只有0.47%,而IPv6失敗率高達7.07%。通過端上優化請求策略,降低接口的併發密度後,IPv6環境和IPv4環境同時提高到99.85%的成功率。

4)接口數據體積越小,請求成功率越高:

HTTP/2和HTTP/1.1都是基於TCP連接的,接口數據體積越小,需要傳輸的TCP包越少,傳輸失敗的概率也就降低了。目前愛奇藝APP正在從gzip轉向壓縮率更高的br(指的是Brotli壓縮算法,詳見:《啟用 Brotli 壓縮算法,對比 Gzip 壓縮 CDN 流量再減少 20%》)。

6、提高魯棒性並防止故障的優化措施

在經過各種優化措施提高網絡成功率後,我們還通過下面幾個措施成功的防止線上故障造成的成功率瞬時下降,提高了網絡請求的魯棒性。

1)超級管道本身的魯棒性:

下面案例顯示使用了超級管道重試的接口錯誤率只有3.95%,而沒有使用超級管道重試的接口錯誤率高達28.96%。這個案例的時間點還沒有使用異地容災IP,在疊加異地容災IP之後,錯誤率曲線幾乎可以抹平。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

2)HTTP重試和原URL重試在v4v6雙棧環境下,優先IPv4:

由於IPv6仍在建設中,有些接口在IPv6的表現弱於IPv4,那麼可以指定重試走IPv4。

3)TLS1.3– 1RTT的節省:

TLS1.3將SSL握手2個RTT降為1個RTT,降低了SSL握手失敗的概率。iOS12.2開始,NSURLSession支持TLS1.3。只需要服務器升級支持TLS1.3即可,端上無須改動。

4)IP複合連接競速:

使用TCP連接測速,目的是剔除壞IP,選擇最優IP,從而提高請求的成功概率。

經上述措施的持續優化,愛奇藝APP在2020Q1末,扣除無網情況後,業務成功率達到了99.7%,而網絡層成功率達到了99.77%。

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

▲ 業務成功率 = 網絡層成功率+HTTP響應成功率+解析成功率

在完成優化後,愛奇藝APP基礎網絡庫的構成如下:

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

如上圖所示,基礎網絡庫各模板的功能作用如下:

1)統一網絡庫:提供一個網絡接口層,所有業務接口都對接使用網絡接口層;

2)統一網絡庫:提供一個網絡封裝層,對接了iOS系統網絡層NSURLSession、ASIHTTPRequest(基於CFNetwork)、和公司自研的長連接網關;

3)網絡統計模塊:將從業務調用開始到回調給業務方的各個環節的耗時及狀態值,變成統計數據,上傳到APM匯合;

4)網絡診斷模塊:對關鍵業務進行診斷,包括dns解析,ping,tcpconnect,trace等工具對具體IP進行分析,分析結果上傳到APM匯合;

5)弱網檢測模塊:通過借鑑Facebook的弱網檢測是基於網速擬合的網絡等級分級,分為網絡情況非常差(2G或者無網)、網絡情況較差(3G)、網絡情況一般、網絡情況較好、網絡情況非常好五個等級;

6)HTTPDNS模塊:有效的解決了運營商劫持問題;

7)超級管道重試:基於HTTP的網關代理,具有異地容災代理能力;

8)ipv4/ipv6模塊:識別端上是ipv4 only環境、v4/v6雙棧還是ipv6 only環境;

9)複合連接模塊:可以在server IP緩存池選出最佳IP,手段包括目標IP連接競速,IP歷史請求統計數據排序;

10)網絡日誌模塊:記錄了最近發生的失敗網絡請求詳細數據和網絡診斷數據。隨反饋一併提交,可以便捷的排查線上網絡問題。

7、未來的目標與可能的優化措施

為了持續優化網絡成功率,下一步目標是扣除無網情況,重點業務成功率達到99.9%。後續考慮的優化措施如下。

1)Multipath:

當Wifi假連接的時可以走蜂窩流量,iOS 7開始支持Multipath特性(詳見:《揭開 iOS 7 之 Multipath TCP 的面紗》)。

2)QUIC:

QUIC是基於UDP的,由於運營商對UDP有針對性的丟包,實測QUIC並沒有體現出優勢。然而,考慮到libcurl在2019已提供完整QUIC能力,NSURLSession不久也會支持QUIC。隨著運營商對UDP包的干擾減少,QUIC的優勢將得到體現。

如果對QUIC協議感興趣,可以讀一讀下面這些文章:

《網絡編程懶人入門(十):一泡尿的時間,快速讀懂QUIC協議》

《技術掃盲:新一代基於UDP的低延時網絡傳輸層協議——QUIC詳解》

《讓互聯網更快:新一代QUIC協議在騰訊的技術實踐分享》

《七牛雲技術分享:使用QUIC協議實現實時視頻直播0卡頓!》

3)智能調度併發:

更精準更靈敏的弱網識別,弱網下對關鍵核心業務進行傾斜。

4)HTTPDNS的push能力:

HTTPDNS打通APM的質量監控體系後,通過push及時下線故障IP。

關於移動端DNS問題上的優化,業內已經有了很多總結,有興趣可以深入研究:

《全面瞭解移動端DNS域名劫持等雜症:技術原理、問題根源、解決方案等》

《美圖App的移動端DNS優化實踐:HTTPS請求耗時減小近半》

《百度APP移動端網絡深度優化實踐分享(一):DNS優化篇》

《移動端網絡優化之HTTP請求的DNS優化》

附錄:更多網絡通信方面的技術資料

《TCP/IP詳解 - 第11章·UDP:用戶數據報協議》

《TCP/IP詳解 - 第17章·TCP:傳輸控制協議》

《TCP/IP詳解 - 第18章·TCP連接的建立與終止》

《TCP/IP詳解 - 第21章·TCP的超時與重傳》

《技術往事:改變世界的TCP/IP協議(珍貴多圖、手機慎點)》

《通俗易懂-深入理解TCP協議(上):理論基礎》

《通俗易懂-深入理解TCP協議(下):RTT、滑動窗口、擁塞處理》

《理論經典:TCP協議的3次握手與4次揮手過程詳解》

《理論聯繫實際:Wireshark抓包分析TCP 3次握手、4次揮手過程》

《計算機網絡通訊協議關係圖(中文珍藏版)》

《UDP中一個包的大小最大能多大?》

《P2P技術詳解(一):NAT詳解——詳細原理、P2P簡介》

《P2P技術詳解(二):P2P中的NAT穿越(打洞)方案詳解(基本原理篇)》

《P2P技術詳解(三):P2P中的NAT穿越(打洞)方案詳解(進階分析篇)》

《P2P技術詳解(四):P2P技術之STUN、TURN、ICE詳解》

《通俗易懂:快速理解P2P技術中的NAT穿透原理》

《高性能網絡編程(一):單臺服務器併發TCP連接數到底可以有多少》

《高性能網絡編程(二):上一個10年,著名的C10K併發連接問題》

《高性能網絡編程(三):下一個10年,是時候考慮C10M併發問題了》

《高性能網絡編程(四):從C10K到C10M高性能網絡應用的理論探索》

《高性能網絡編程(五):一文讀懂高性能網絡編程中的I/O模型》

《高性能網絡編程(六):一文讀懂高性能網絡編程中的線程模型》

《Java的BIO和NIO很難懂?用代碼實踐給你看,再不懂我轉行!》

《不為人知的網絡編程(一):淺析TCP協議中的疑難雜症(上篇)》

《不為人知的網絡編程(二):淺析TCP協議中的疑難雜症(下篇)》

《不為人知的網絡編程(三):關閉TCP連接時為什麼會TIME_WAIT、CLOSE_WAIT》

《不為人知的網絡編程(四):深入研究分析TCP的異常關閉》

《不為人知的網絡編程(五):UDP的連接性和負載均衡》

《不為人知的網絡編程(六):深入地理解UDP協議並用好它》

《不為人知的網絡編程(七):如何讓不可靠的UDP變的可靠?》

《不為人知的網絡編程(八):從數據傳輸層深度解密HTTP》

《不為人知的網絡編程(九):理論聯繫實際,全方位深入理解DNS》

《網絡編程懶人入門(一):快速理解網絡通信協議(上篇)》

《網絡編程懶人入門(二):快速理解網絡通信協議(下篇)》

《網絡編程懶人入門(三):快速理解TCP協議一篇就夠》

《網絡編程懶人入門(四):快速理解TCP和UDP的差異》

《網絡編程懶人入門(五):快速理解為什麼說UDP有時比TCP更有優勢》

《網絡編程懶人入門(六):史上最通俗的集線器、交換機、路由器功能原理入門》

《網絡編程懶人入門(七):深入淺出,全面理解HTTP協議》

《網絡編程懶人入門(八):手把手教你寫基於TCP的Socket長連接》

《網絡編程懶人入門(九):通俗講解,有了IP地址,為何還要用MAC地址?》

《網絡編程懶人入門(十):一泡尿的時間,快速讀懂QUIC協議》

《網絡編程懶人入門(十一):一文讀懂什麼是IPv6》

《技術掃盲:新一代基於UDP的低延時網絡傳輸層協議——QUIC詳解》

《讓互聯網更快:新一代QUIC協議在騰訊的技術實踐分享》

《現代移動端網絡短連接的優化手段總結:請求速度、弱網適應、安全保障》

《聊聊iOS中網絡編程長連接的那些事》

《移動端IM開發者必讀(一):通俗易懂,理解移動網絡的“弱”和“慢”》

《移動端IM開發者必讀(二):史上最全移動弱網絡優化方法總結》

《IPv6技術詳解:基本概念、應用現狀、技術實踐(上篇)》

《IPv6技術詳解:基本概念、應用現狀、技術實踐(下篇)》

《從HTTP/0.9到HTTP/2:一文讀懂HTTP協議的歷史演變和設計思路》

《腦殘式網絡編程入門(一):跟著動畫來學TCP三次握手和四次揮手》

《腦殘式網絡編程入門(二):我們在讀寫Socket時,究竟在讀寫什麼?》

《腦殘式網絡編程入門(三):HTTP協議必知必會的一些知識》

《腦殘式網絡編程入門(四):快速理解HTTP/2的服務器推送(Server Push)》

《腦殘式網絡編程入門(五):每天都在用的Ping命令,它到底是什麼?》

《腦殘式網絡編程入門(六):什麼是公網IP和內網IP?NAT轉換又是什麼鬼?》

《腦殘式網絡編程入門(七):面視必備,史上最通俗計算機網絡分層詳解》

《腦殘式網絡編程入門(八):你真的瞭解127.0.0.1和0.0.0.0的區別?》

《以網遊服務端的網絡接入層設計為例,理解實時通信的技術挑戰》

《邁向高階:優秀Android程序員必知必會的網絡基礎》

《全面瞭解移動端DNS域名劫持等雜症:技術原理、問題根源、解決方案等》

《美圖App的移動端DNS優化實踐:HTTPS請求耗時減小近半》

《Android程序員必知必會的網絡通信傳輸層協議——UDP和TCP》

《IM開發者的零基礎通信技術入門(一):通信交換技術的百年發展史(上)》

《IM開發者的零基礎通信技術入門(二):通信交換技術的百年發展史(下)》

《IM開發者的零基礎通信技術入門(三):國人通信方式的百年變遷》

《IM開發者的零基礎通信技術入門(四):手機的演進,史上最全移動終端發展史》

《IM開發者的零基礎通信技術入門(五):1G到5G,30年移動通信技術演進史》

《IM開發者的零基礎通信技術入門(六):移動終端的接頭人——“基站”技術》

《IM開發者的零基礎通信技術入門(七):移動終端的千里馬——“電磁波”》

《IM開發者的零基礎通信技術入門(八):零基礎,史上最強“天線”原理掃盲》

《IM開發者的零基礎通信技術入門(九):無線通信網絡的中樞——“核心網”》

《IM開發者的零基礎通信技術入門(十):零基礎,史上最強5G技術掃盲》

《IM開發者的零基礎通信技術入門(十一):為什麼WiFi信號差?一文即懂!》

《IM開發者的零基礎通信技術入門(十二):上網卡頓?網絡掉線?一文即懂!》

《IM開發者的零基礎通信技術入門(十三):為什麼手機信號差?一文即懂!》

《IM開發者的零基礎通信技術入門(十四):高鐵上無線上網有多難?一文即懂!》

《IM開發者的零基礎通信技術入門(十五):理解定位技術,一篇就夠》

《百度APP移動端網絡深度優化實踐分享(一):DNS優化篇》

《百度APP移動端網絡深度優化實踐分享(二):網絡連接優化篇》

《百度APP移動端網絡深度優化實踐分享(三):移動端弱網優化篇》

《技術大牛陳碩的分享:由淺入深,網絡編程學習經驗乾貨總結》

《可能會搞砸你的面試:你知道一個TCP連接上能發起多少個HTTP請求嗎?》

《知乎技術分享:知乎千萬級併發的高性能長連接網關技術實踐》

《5G時代已經到來,TCP/IP老矣,尚能飯否?》

《愛奇藝移動網絡優化實踐分享:網絡請求成功率優化篇(iOS端)》

>> 更多同類文章 ……

歡迎關注我的“即時通訊技術圈”公眾號:

愛奇藝移動端網絡優化實踐分享:網絡請求成功率優化篇

(本文已同步發佈於:
http://www.52im.net/thread-2981-1-1.html)


分享到:


相關文章: