OKhtt原理以及異步執(zhí)行過程

OKhtt原理以及異步執(zhí)行過程

? ? 先上圖,這是Okhttp官網(wǎng)文檔的一張OKhttp請求執(zhí)行流程和經(jīng)過的攔截器泼舱,并且服務(wù)器響應(yīng)的時(shí)候經(jīng)過的攔截器躁绸。

? ? ? ? 大家看這張圖的時(shí)候按照流程執(zhí)行裕循,這是okhttp的請求執(zhí)行過程,從應(yīng)用發(fā)出request净刮,到應(yīng)用收到response剥哑,期間經(jīng)歷了N個(gè)攔截器,可以看出Okhttp的攔截器在整個(gè)請求的過程中起到了重大作用,扮演者中要的角色庭瑰。

? ? 攔截器的作用:

官方文檔翻譯

Rewriting Requests

Interceptors can add, remove, or replace request headers. They can also transform the body of those requests that have one. For example, you can use an application interceptor to add request body compression if you're connecting to a webserver known to support it.

? ? ? ? ? ?攔截器可以對每一個(gè)請求頭中的信息進(jìn)行星持,添加,移除弹灭,或者替換督暂。如有請求中有請求體的話還可以對請求體里里面的內(nèi)容做轉(zhuǎn)換。比如穷吮,你可以給你的應(yīng)用增加一個(gè)”內(nèi)容壓縮的攔截器“逻翁,對請求體中的內(nèi)容進(jìn)行壓縮,前提是你請求的服務(wù)器能支持你這種壓縮后的請求內(nèi)容捡鱼,所以要實(shí)現(xiàn)類型功能請后端必須溝通好八回,比如前端采用什么樣的壓縮算法,后端接收到請求后,采用相同的算法解壓缠诅。不過一般來說我們都不會(huì)采用這種攔截器溶浴,因?yàn)閛khttp 默認(rèn)就支持GZIP壓縮

OKhttp3 核心

?Okhttp3 是一個(gè)高性能網(wǎng)絡(luò)請求框架,支持支持HTTPS/HTTP2/WebSocket 管引,其核心有一下幾點(diǎn):

????1士败、采用責(zé)任鏈方式的攔截器,實(shí)現(xiàn)分成處理網(wǎng)絡(luò)請求褥伴,讓用戶對網(wǎng)絡(luò)請求實(shí)現(xiàn)了更好的擴(kuò)展

????2谅将、GZIP處理降低了下載數(shù)據(jù)的大小

????3、支持http 緩存

????4重慢、采用線程池(thread pool)和連接池(socket pool)解決多并發(fā)問題饥臂,同時(shí)連接池采支持多路復(fù)用(http2才支持多路復(fù)用,單路復(fù)用指的是似踱,個(gè)socket 只有把一個(gè)請求發(fā)送完成后隅熙,才能繼續(xù)發(fā)送第二個(gè)請求,多路復(fù)用可以讓一個(gè)socket 同時(shí)發(fā)送多個(gè)請求的數(shù)據(jù)屯援,內(nèi)部會(huì)自動(dòng)維護(hù)順序)猛们,減少連接創(chuàng)建開銷

????5、底層采用 socket 和服務(wù)器進(jìn)行連接狞洋。

????6弯淘、采用okio 實(shí)現(xiàn)高效的io流讀寫

OkhttpCore(內(nèi)置5大核心攔截器)

上圖攔截器流程示意圖中,其中OkhttCore 包含了五大核心攔截器吉懊,它們承擔(dān)了整個(gè)網(wǎng)絡(luò)請求的全部工作庐橙。

1.RetryAndFollowUpInterceptor

RetryAndFollowUpInterceptor 的作用,看到該攔截器的名稱就知道借嗽,它就是一個(gè)負(fù)責(zé)失敗重連和重定向的攔截器态鳖。它是 Okhttp 內(nèi)置的第一個(gè)攔截器,通過 while (true) 的死循環(huán)來進(jìn)行對異常結(jié)果或者響應(yīng)結(jié)果判斷是否要進(jìn)行重新請求恶导。

引用一篇網(wǎng)上的重試機(jī)制

2.BridgeInterceptor

BridgeInterceptor 為用戶構(gòu)建的一個(gè) Request 請求轉(zhuǎn)化為能夠進(jìn)行網(wǎng)絡(luò)訪問的請求浆竭,同時(shí)將網(wǎng)絡(luò)請求回來的響應(yīng) Response 轉(zhuǎn)化為用戶可用的 Response。比如惨寿,涉及的網(wǎng)絡(luò)文件的類型和網(wǎng)頁的編碼邦泄,返回的數(shù)據(jù)的解壓處理等等。

3.CacheInterceptor

CacheInterceptor 根據(jù) OkHttpClient 對象的配置以及緩存策略對請求值進(jìn)行緩存裂垦。

可以參考http 的緩存機(jī)制:

4.ConnectInterceptor

ConnectInterceptor 在 OKHTTP 底層是通過 SOCKET 的方式于服務(wù)端進(jìn)行連接的顺囊,并且在連接建立之后會(huì)通過 OKIO 獲取通向 server 端的輸入流 Source 和輸出流 Sink。

5.CallServerInterceptor

CallServerInterceptor 在 ConnectInterceptor 攔截器的功能就是負(fù)責(zé)與服務(wù)器建立 Socket 連接蕉拢,并且創(chuàng)建了一個(gè) HttpStream 它包括通向服務(wù)器的輸入流和輸出流特碳。而接下來的 CallServerInterceptor 攔截器的功能使用 HttpStream 與服務(wù)器進(jìn)行數(shù)據(jù)的讀寫操作的诚亚。

自定義攔截器

1.應(yīng)用攔截器 Application Interceptor

2.網(wǎng)絡(luò)攔截器 NetWork Interceptor

他們的異同:

相同點(diǎn)

  1)都能對server返回的response進(jìn)行攔截

? ? ? 2)這兩種攔截器本質(zhì)上都是基于Interceptor接口,由開發(fā)者實(shí)現(xiàn)這個(gè)接口午乓,然后將自定義的Interceptor類的對象設(shè)置到okhttpClient對象中站宗,所以,本質(zhì)上沒什么不同益愈,都是Interceptor的實(shí)現(xiàn)類的對象份乒。

  3)兩者都會(huì)被add到OkHttpClient內(nèi)的一個(gè)ArrayList中。當(dāng)請求執(zhí)行的時(shí)候腕唧,多個(gè)攔截器會(huì)依次執(zhí)行(list本身就是有序的)。

不同點(diǎn)

  1)okhttpClient添加兩種攔截器的api不同瘾英。添加應(yīng)用攔截器的接口是addInterceptor()枣接,而添加網(wǎng)絡(luò)攔截器的接口是addNetworkInterceptor().

   2)兩者負(fù)責(zé)的區(qū)域不同,從最上方圖中可以看出缺谴,應(yīng)用攔截器作用于okhttpCore到Application之間但惶,網(wǎng)絡(luò)攔截器作用于 network和okhttpCore之間

   3)在某種特殊情況下(比如:訪問了一個(gè)url,結(jié)果這個(gè)url發(fā)生了重定向)湿蛔,網(wǎng)絡(luò)攔截器有可能被執(zhí)行多次膀曾,但是 不論任何情況,application只會(huì)被執(zhí)行一次阳啥。

? ? 核心源碼?


? 構(gòu)建完成Request的后通關(guān)newCall發(fā)送請求返回一個(gè)Call對象后執(zhí)行異步請求

進(jìn)到RealCall類中的異步方法? 看到最后一行代碼添谊,okhttpclient對象調(diào)用dispatcher方法返回一個(gè)dispatcher對象進(jìn)行調(diào)用dispatcher中的異步方法將call放入異步任務(wù)中并將匿名異步任務(wù)對象傳入道此方法中,? 這里的使用的鏈?zhǔn)骄幊?/p>


進(jìn)入到disparcher中找到enqueue方法

這里首先是將異步任務(wù)添加到了一個(gè)準(zhǔn)備任務(wù)隊(duì)列中察迟,

if判斷中是對正在執(zhí)行的任務(wù)隊(duì)列或者準(zhǔn)備執(zhí)行的任務(wù)隊(duì)列中找之前執(zhí)行的異步任務(wù) AsyncCall斩狱,首先去準(zhǔn)備任務(wù)隊(duì)列中去尋找,找不到了再去正在執(zhí)行的任務(wù)隊(duì)列中去找扎瓶,

找到之后去判斷是否為空所踊,不為空的話會(huì)將找的異步任務(wù)傳入ReakCall中賦值給本次異步任務(wù)(AtomicInteger 一個(gè)計(jì)數(shù)器,線程安全)概荷,這個(gè)后面會(huì)提到秕岛。

最后調(diào)用的promoteAndExecute()? 這個(gè)方法大家從字面意思上看大概也知道這就是準(zhǔn)備執(zhí)行了,

Dispatcher 的promoteAndExecute 方法:


最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末误证,一起剝皮案震驚了整個(gè)濱河市继薛,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌雷厂,老刑警劉巖惋增,帶你破解...
    沈念sama閱讀 217,277評論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異改鲫,居然都是意外死亡诈皿,警方通過查閱死者的電腦和手機(jī)林束,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,689評論 3 393
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來稽亏,“玉大人壶冒,你說我怎么就攤上這事〗厍福” “怎么了胖腾?”我有些...
    開封第一講書人閱讀 163,624評論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長瘪松。 經(jīng)常有香客問我咸作,道長,這世上最難降的妖魔是什么宵睦? 我笑而不...
    開封第一講書人閱讀 58,356評論 1 293
  • 正文 為了忘掉前任记罚,我火速辦了婚禮,結(jié)果婚禮上壳嚎,老公的妹妹穿的比我還像新娘桐智。我一直安慰自己,他們只是感情好烟馅,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,402評論 6 392
  • 文/花漫 我一把揭開白布说庭。 她就那樣靜靜地躺著,像睡著了一般郑趁。 火紅的嫁衣襯著肌膚如雪刊驴。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,292評論 1 301
  • 那天穿撮,我揣著相機(jī)與錄音缺脉,去河邊找鬼。 笑死悦穿,一個(gè)胖子當(dāng)著我的面吹牛攻礼,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播栗柒,決...
    沈念sama閱讀 40,135評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼礁扮,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了瞬沦?” 一聲冷哼從身側(cè)響起太伊,我...
    開封第一講書人閱讀 38,992評論 0 275
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎逛钻,沒想到半個(gè)月后僚焦,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,429評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡曙痘,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,636評論 3 334
  • 正文 我和宋清朗相戀三年芳悲,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了立肘。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,785評論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡名扛,死狀恐怖谅年,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情肮韧,我是刑警寧澤融蹂,帶...
    沈念sama閱讀 35,492評論 5 345
  • 正文 年R本政府宣布,位于F島的核電站弄企,受9級特大地震影響超燃,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜拘领,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,092評論 3 328
  • 文/蒙蒙 一淋纲、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧院究,春花似錦、人聲如沸本涕。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,723評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽菩颖。三九已至样漆,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間晦闰,已是汗流浹背放祟。 一陣腳步聲響...
    開封第一講書人閱讀 32,858評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留呻右,地道東北人跪妥。 一個(gè)月前我還...
    沈念sama閱讀 47,891評論 2 370
  • 正文 我出身青樓,卻偏偏與公主長得像声滥,于是被迫代替她去往敵國和親眉撵。 傳聞我的和親對象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,713評論 2 354

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

  • 前言 用OkHttp很久了落塑,也看了很多人寫的源碼分析纽疟,在這里結(jié)合自己的感悟,記錄一下對OkHttp源碼理解的幾點(diǎn)心...
    Java小鋪閱讀 1,518評論 0 13
  • Activity的生命周期 正常的流程: onCreate():被創(chuàng)建的時(shí)候被回調(diào)憾赁, onStart():Acti...
    安夢_4de8閱讀 418評論 0 0
  • 關(guān)于okhttp是一款優(yōu)秀的網(wǎng)絡(luò)請求框架污朽,關(guān)于它的源碼分析文章有很多,這里分享我在學(xué)習(xí)過程中讀到的感覺比較好的文章...
    蕉下孤客閱讀 3,602評論 2 38
  • 用OkHttp很久了龙考,也看了很多人寫的源碼分析蟆肆,在這里結(jié)合自己的感悟矾睦,記錄一下對OkHttp源碼理解的幾點(diǎn)心得。 ...
    藍(lán)灰_q閱讀 4,279評論 4 34
  • 第七天 早上起來感覺特別“累”----精力不夠颓芭,電量75%… 上午:娃帶車上…去銀行…去供應(yīng)商…送娃去媽媽上班的學(xué)...
    安貞閱讀 267評論 0 0