Retrofit2.0 源碼思路整理

看了下之前4月份寫的Retrofit使用和 源碼分析,發(fā)現(xiàn)县好,源碼這種東西围橡,忘記比較快,只能知道大概是怎么的缕贡,但是從頭去看翁授,花點時間拣播,可以回顧,但是發(fā)現(xiàn)思路比較亂收擦,或許是前一次看了太久了贮配,于是整理下,梳理下


Retrofit 2.0 .png

思路整理:

1.創(chuàng)建retrofit

Retrofit retrofit = new Retrofit.Builder() 
.baseUrl("http://fanyi.youdao.com/") 
.addConverterFactory(GsonConverterFactory.create()) 
.build();
1.1第一步 Retrofit :

使用建造者模式建立Retrofit對象 塞赂,首先有個linkedhashMap數(shù)據(jù)結(jié)構(gòu) (后面有原因)存放的 key method value 是ServerMethod 泪勒,這個ServerMethod 是網(wǎng)絡(luò)請求的相關(guān)配置,包括了 baseURL 網(wǎng)絡(luò)請求轉(zhuǎn)換器 網(wǎng)絡(luò)請求適配器 網(wǎng)絡(luò)請求工廠 回調(diào)執(zhí)行器 宴猾,還有就是上面的5個相關(guān)的 網(wǎng)絡(luò)請求工廠 適配器工廠集合 List 轉(zhuǎn)換器工廠集合List 加上一個標(biāo)志 作用是判斷是不是要提前檢查接口注解進行轉(zhuǎn)換酣藻, 第一步 就是配置好這5個 和 linkedhashmap 特別說下 網(wǎng)絡(luò)請求執(zhí)行器(Call)——callAdapter 網(wǎng)絡(luò)請求執(zhí)行器的適配器——適配器是哪里來的?是callAdapterFactory生產(chǎn)的鳍置,在retrofit 中這個適配器有4種辽剧,默認(rèn)的excutorCallAdapterFactory.java8 Guava ,Rxjava,,,,, 在retrofit 中 執(zhí)行器默認(rèn)是okhttpcall 比如要將這個默認(rèn)請求執(zhí)行器轉(zhuǎn)換成不同平臺的 比如rxjava 調(diào)用時候就要添加 add CallFactroy(RxjavacallAdapterFactory.create());
后面的幾個步驟都是為了配置好上面的東西,

1.2.第二步build()

這個類的成員變量和Retrofit的是對應(yīng)的税产,而配置就是通過這個類來配置的怕轿, 無參調(diào)用了自己的有參構(gòu)造,傳入的參數(shù)是PlatForm.get()——get() 返回的是一個靜態(tài)變量辟拷,靜態(tài)變量是調(diào)用——findPlatForm方法撞羽,這個方法中通過calss.forName("adnrod.os.build"),也就是調(diào)用里面靜態(tài)構(gòu)造 判斷這個build .version,sdk.int !=0 就new Android()是安卓平臺創(chuàng)建一個android對象—— android() 繼承platform主要是返回數(shù)據(jù)做線程切換回主線程顯示UI的 重寫了defaultcallBack方法衫冻,這個newHandler 并綁定主線程诀紊,然后post 切換線程 線程切換的流程是 先從第一個重寫的defalutCallAdapter
Factroy 生成一個call對象,然后用這個對象隅俘,enquene(callback )從而調(diào)用第二個重寫方法的excute通過handler完成 ——最后返回一個platForm對象 有參構(gòu)造:首先是接受上面的platform對象邻奠,然后往成員list,存放數(shù)據(jù)轉(zhuǎn)換器factory的为居,添加一個new BuiltInConvers對象 這個是一個內(nèi)置的數(shù)據(jù)轉(zhuǎn)換器碌宴,懟他初始化,
整個是設(shè)置了默認(rèn)值蒙畴。沒有正真為retrofit成員變量賦值

1.3.第3步baseUrl

首先檢查是否為空——然后調(diào)用parse ()這個parse 是第二步 build 的方法檢查一些符號去吧string類型轉(zhuǎn)換成httpurl 贰镣,包括方案scheme,成功呢繼續(xù)膳凝,—— 再調(diào)用 baseUrl(httpurl url) 判斷是否已斜杠結(jié)束 不是報錯碑隆。
這里主要是為build 類的 url成員變量賦值

1.4.第4步
add ConverterFactory( GsonConverterFactory.create())

GsonConverterFactory.create() 創(chuàng)建了一個含有Gson對象實例的GsonConverterFactory,并返回給addConverterFactory()并
addConvertFactory方法蹬音,就是網(wǎng)build類的 轉(zhuǎn)換器工廠list 添加 上面的含有g(shù)son對象的工廠類上煤,
Retrofit默認(rèn)使用Gson進行解析 如果是其他數(shù)據(jù)格式 可以自定義繼承convert factory 就可以

1.5..第5步 build

配置網(wǎng)絡(luò)請求執(zhí)行器,配置回調(diào)方法執(zhí)行器祟绊,網(wǎng)絡(luò)請求適配器工廠楼入,數(shù)據(jù)轉(zhuǎn)換器工廠 然后new Retrofit 返回
建造者模式哥捕,所以開發(fā)者并不需要關(guān)心配置細節(jié)就可以創(chuàng)建好Retrofit實例,

2嘉熊、創(chuàng)建網(wǎng)絡(luò)請求接口實例

    1,定義    接受網(wǎng)絡(luò)請求實體類
    2.定義接口類
    3.接口     j   =  retofit.create(接口.class)
    4.Call<1的對象>  call    =   j .接口中的getCall()

概述:Retrofit使用外觀模式和動態(tài)代理遥赚,調(diào)用create()創(chuàng)建網(wǎng)絡(luò)請求接口的實例,同時通過接口的注解阐肤,進行網(wǎng)絡(luò)請求參數(shù)的配置
create(): 首先判斷是不是接口凫佛,并且只能是實現(xiàn)一個接口 ,然后判斷之前說的那個標(biāo)志位孕惜,是否需要提前校驗愧薛,如果需要,就調(diào)用earlyvalitedMethod() 在這方法中 用到了反射衫画,獲取到所有的方法毫炉,然后獲取到平臺,然后判斷如果不是系統(tǒng)方法削罩。調(diào)用——loadServiceMethod() : 這個方法通過傳入的參數(shù)method 去 Retrofit類中的成員中的那個 LinkedHashMap 中獲取瞄勾,如果為空就直接new ServiceMethod.builder(this,method ).build()并存到map 中, 如果不需要提前驗證就通過后面的動態(tài)代理解析對應(yīng)方法
這個create()返回的就是創(chuàng)建網(wǎng)絡(luò)請求接口的一個動態(tài)代理的方法弥激,調(diào)用并返回請求接口的實例进陡, 目的就是為了去拿到網(wǎng)絡(luò)請求接口上的所有注解, 在invoke() 中業(yè)調(diào)用了loadServiceMethod() —— 吧這個返回的和參數(shù)封裝到new OkhttpCall中—— 再調(diào)用ServiceMethod.callAdapter.adpt(上面封裝的call) 好處是調(diào)用集中到這個invoke 方法中微服,并且獲取到接口上的注解趾疚,方便封裝serviceMethed new ServiceMethod.builder(this,method ).build() 也分3個步驟,一是配置以蕴,2是獲取方法的注解 方法的參數(shù) build 也是從根據(jù)接口方法返回值注解糙麦,獲取對應(yīng)的網(wǎng)絡(luò)請求適配器,適配器參數(shù) 創(chuàng)建對應(yīng)的轉(zhuǎn)換器 然后在遍歷解析方法注解舒裤,也就是調(diào)用ParseMethodAnnotation() 這里面就是解析 get post delate等請求 然后是獲取參數(shù) 數(shù)量喳资。遍歷 給沒個參數(shù) 有個paramshandler 去解析參數(shù)的注解,這個就是 new ServiceMethod.builder(this,method ).build() 配置完網(wǎng)絡(luò)請求參數(shù)(即配置好ServiceMethod對象) 然后封裝到okhttpcall 然后再調(diào)用上面配置完網(wǎng)絡(luò)請求參數(shù)的serviceMethod方法的callAdapter ,的adapt() 安卓默認(rèn)是call Rxjava 是Observable《》

4.Call<1的對象> call = j .接口中的getCall()
j實際是動態(tài)代理的對象并不是正真網(wǎng)絡(luò)請求接口創(chuàng)建的對象腾供, 調(diào)用這個方法時候被動態(tài)代理對象攔截,被proxy.newinstance 攔截調(diào)用自己的indicatorHnadler 的invoke方法鲜滩, 傳入 代理對象proxy method args 接下來反射獲取注解信息結(jié)合agrs 創(chuàng)建serviceMethod對象 最終創(chuàng)建并返回一個OkHttpCall類型的Call對象 okhttp call 是 okhttp 的封裝類伴鳖,但是此時還不能發(fā)送請求,還要創(chuàng)建請求對象徙硅。

3.執(zhí)行網(wǎng)絡(luò)請求

同步請求:OkHttpCall.execute()
異步請求:OkHttpCall.enqueue()
也就是execute包含下面的3個流程
1.根據(jù)前面的paramshandler 解析參數(shù)榜聂,結(jié)合serviceMethod 對象創(chuàng)建一個Request對象
createRawCall()創(chuàng)建okhttp3,的request對象
2.使用ok的request發(fā)送請求。
call.execute()
3.對返回的數(shù)據(jù)使用之前設(shè)置的GsonConvertFactory解析得到一個Response《T》對象
response( call.execute()) 判斷返回狀態(tài)碼 調(diào)用response嗓蘑。success (body )生成 response類
為了提高效率须肆,Retrofit還會對解析過的請求ServiceMethod進行緩存
4.異步的 就有一個進行線程切換從而在主線程處理返回的數(shù)據(jù)結(jié)果 若使用RXjava直接回調(diào)到主線程
區(qū)別:線程切換流程:1.ExcuterCallAdapterFactry 生成一個ExcutercallbackCall
2.調(diào)用1.的enquene (callback) 從而調(diào)用MaindthreadExcuter 的execute()通過handler 切換

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末匿乃,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子豌汇,更是在濱河造成了極大的恐慌幢炸,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,366評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件拒贱,死亡現(xiàn)場離奇詭異宛徊,居然都是意外死亡,警方通過查閱死者的電腦和手機逻澳,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,521評論 3 395
  • 文/潘曉璐 我一進店門闸天,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人斜做,你說我怎么就攤上這事苞氮。” “怎么了瓤逼?”我有些...
    開封第一講書人閱讀 165,689評論 0 356
  • 文/不壞的土叔 我叫張陵葱淳,是天一觀的道長。 經(jīng)常有香客問我抛姑,道長赞厕,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,925評論 1 295
  • 正文 為了忘掉前任定硝,我火速辦了婚禮皿桑,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘蔬啡。我一直安慰自己诲侮,他們只是感情好,可當(dāng)我...
    茶點故事閱讀 67,942評論 6 392
  • 文/花漫 我一把揭開白布箱蟆。 她就那樣靜靜地躺著沟绪,像睡著了一般。 火紅的嫁衣襯著肌膚如雪空猜。 梳的紋絲不亂的頭發(fā)上绽慈,一...
    開封第一講書人閱讀 51,727評論 1 305
  • 那天,我揣著相機與錄音辈毯,去河邊找鬼坝疼。 笑死,一個胖子當(dāng)著我的面吹牛谆沃,可吹牛的內(nèi)容都是我干的钝凶。 我是一名探鬼主播,決...
    沈念sama閱讀 40,447評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼唁影,長吁一口氣:“原來是場噩夢啊……” “哼耕陷!你這毒婦竟也來了掂名?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,349評論 0 276
  • 序言:老撾萬榮一對情侶失蹤哟沫,失蹤者是張志新(化名)和其女友劉穎饺蔑,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體南用,經(jīng)...
    沈念sama閱讀 45,820評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡膀钠,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,990評論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了裹虫。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片肿嘲。...
    茶點故事閱讀 40,127評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖筑公,靈堂內(nèi)的尸體忽然破棺而出雳窟,到底是詐尸還是另有隱情,我是刑警寧澤匣屡,帶...
    沈念sama閱讀 35,812評論 5 346
  • 正文 年R本政府宣布封救,位于F島的核電站,受9級特大地震影響捣作,放射性物質(zhì)發(fā)生泄漏誉结。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,471評論 3 331
  • 文/蒙蒙 一券躁、第九天 我趴在偏房一處隱蔽的房頂上張望惩坑。 院中可真熱鬧,春花似錦也拜、人聲如沸以舒。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,017評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽蔓钟。三九已至,卻和暖如春卵贱,著一層夾襖步出監(jiān)牢的瞬間滥沫,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,142評論 1 272
  • 我被黑心中介騙來泰國打工艰赞, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留佣谐,地道東北人。 一個月前我還...
    沈念sama閱讀 48,388評論 3 373
  • 正文 我出身青樓方妖,卻偏偏與公主長得像,于是被迫代替她去往敵國和親罚攀。 傳聞我的和親對象是個殘疾皇子党觅,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,066評論 2 355

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