Retrofit+Rxjava+OKHttp3之Session過期處理

前言
在app實(shí)際請(qǐng)求服務(wù)器接口的過程中常柄,經(jīng)常會(huì)遇到session過期的情況忌堂,這時(shí)候需要我們重新登錄刷新session。
期初實(shí)現(xiàn)的方案是,發(fā)現(xiàn)session過期需要登錄時(shí)寝并,直接跳轉(zhuǎn)到登錄界面鞭衩,登陸后跳轉(zhuǎn)首頁苛白。
但更合理的情形是一旦發(fā)現(xiàn)session過期焰檩,直接調(diào)用登錄接口刷新session,之后繼續(xù)原來的業(yè)務(wù)膘婶,即在此請(qǐng)求原來的業(yè)務(wù)接口缺前。
本文就將針對(duì)使用OKHttp3的底層網(wǎng)路框架的情形,說一下如何實(shí)現(xiàn)session過期的統(tǒng)一處理悬襟。
有興趣的同學(xué)可以加入學(xué)習(xí)小組QQ群: 193765960做進(jìn)一步的討論衅码。

版權(quán)歸作者所有,轉(zhuǎn)發(fā)請(qǐng)注明出處:http://www.reibang.com/u/d43d948bef39

1. 總體方案:攔截器

1)在網(wǎng)絡(luò)請(qǐng)求的底層OKhttp層設(shè)置攔截器脊岳,攔截網(wǎng)絡(luò)請(qǐng)求和響應(yīng)數(shù)據(jù)逝段。
2)分析響應(yīng)數(shù)據(jù)垛玻,根據(jù)響應(yīng)的狀態(tài)判斷是否發(fā)生session過期。
3)如果沒有過期奶躯,則正常返回響應(yīng)數(shù)據(jù)帚桩。
4)如果發(fā)生session過期,則取消當(dāng)前響應(yīng)數(shù)據(jù)嘹黔,生成刷新session的請(qǐng)求(一般是登錄請(qǐng)求)账嚎。
5)如果session刷新成功,根據(jù)原來業(yè)務(wù)的請(qǐng)求數(shù)據(jù)從新發(fā)起請(qǐng)求儡蔓。
6)如果session刷新失敗郭蕉,則返回session過期的異常響應(yīng),在上層解析該響應(yīng)后跳轉(zhuǎn)登錄界面喂江。
7)從登錄界面重新登陸后召锈,跳轉(zhuǎn)到首頁。

2. 攔截器的實(shí)現(xiàn)

import okhttp3.Interceptor;
import okhttp3.Request;
import okhttp3.Response;

public class SessionKeyInterceptor implements Interceptor {
    @Override
    public Response intercept(Chain chain) throws IOException {
        Request old_request = chain.request();
        Response old_response = chain.proceed(old_request);
        //下面這行代碼注意下获询,不要使用Gson等工具對(duì)old_response.body等直接轉(zhuǎn)化涨岁,會(huì)出問題的。
        //RequestHelper: 工具類小伙伴們可以加群吉嚣,單獨(dú)找我索要
        JSONObject obj = RequestHelper.response2Object(old_response);
        //如果session過期梢薪,則重新登錄獲取sessionkey
        if (obj != null && TextUtils.equals(obj .optString("error_code"), MyConfig.getSessionKeyErrorNumber())) {

            //上層注入的請(qǐng)求MyRequest 
            MyRequest loginp = LoginUtils.getRequest();
            if(null == loginp || loginp.size()==0){
                return old_response;
            }

            if(null == LoginUtil.getLoginApi()){
                return originalResponse;
            }

            Request login_request = RequestHelper.buildGetRequest(loginparam, LoginUtils.getLoginApi());
            Response login_response = chain.proceed(login_request);
            if (login_response.isSuccessful()) {
                JSONObject obj2 = RequestHelper.response2Object(login_response);
                if(obj2!= null && (TextUtils.equals(obj2.optString("error_code"), "http://api請(qǐng)求成功的狀態(tài)碼"))){
                    //登錄成功,執(zhí)行原始request
                    String sessionKey = "";
                    try {
                        sessionKey = obj2.getJSONObject("jsondata").getString("session_key");
                    } catch (JSONException e) {
                        e.printStackTrace();
                    }
                    login_response.body().close();
                    Map<String, Object> param = RequestHelper.parseParams(old_request);
                    //更新old_request的session_key等可變參數(shù)
                    param.put("sessionKey",sessionKey);
                    MyRequest request = new MyRequest ();
                    request.put(param);
                    originalRequest = RequestHelper.handler(request, old_request);
                    originalResponse.body().close();
                    return chain.proceed(old_request);
                }
            }
        }
        return old_response;
    }

基于項(xiàng)目代碼安全的需要瓦戚,對(duì)以上代碼做了處理沮尿,不過大體的思路都是可用的

3. 登錄請(qǐng)求的上層注入

為了更好地適用于不同的項(xiàng)目丛塌,和后期代碼的維護(hù)较解,判斷session是否過期的判斷依據(jù)采用上層配置并注入的方式。
當(dāng)然赴邻,您也可以直接在Okhttp層寫死印衔,開發(fā)難度會(huì)簡(jiǎn)單很多,只是后期維護(hù)或者做項(xiàng)目移植時(shí)需要特別注意修改姥敛。
發(fā)起session刷新的接口請(qǐng)求參數(shù)也是同樣的處理奸焙。不再一一贅述。

4. 存在問題

長(zhǎng)時(shí)間在后臺(tái)靜默APP彤敛,數(shù)據(jù)有可能會(huì)被gc掉与帆,所以這種情況下,系統(tǒng)不會(huì)無縫的去成功刷新session并執(zhí)行目標(biāo)請(qǐng)求的業(yè)務(wù)邏輯墨榄,而是會(huì)直接啟動(dòng)登錄界面玄糟。
這個(gè)攔截器,僅僅針對(duì)了session過期的情況袄秩,其實(shí)功能邏輯具有通用性阵翎,可以考慮和業(yè)務(wù)解耦逢并,通過注入的方式支持更多異常的無縫處理。

以上郭卫。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末砍聊,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子贰军,更是在濱河造成了極大的恐慌玻蝌,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,036評(píng)論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件词疼,死亡現(xiàn)場(chǎng)離奇詭異灶伊,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)寒跳,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,046評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門聘萨,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人童太,你說我怎么就攤上這事米辐。” “怎么了书释?”我有些...
    開封第一講書人閱讀 164,411評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵翘贮,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我爆惧,道長(zhǎng)狸页,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,622評(píng)論 1 293
  • 正文 為了忘掉前任扯再,我火速辦了婚禮芍耘,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘熄阻。我一直安慰自己斋竞,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,661評(píng)論 6 392
  • 文/花漫 我一把揭開白布秃殉。 她就那樣靜靜地躺著坝初,像睡著了一般。 火紅的嫁衣襯著肌膚如雪钾军。 梳的紋絲不亂的頭發(fā)上鳄袍,一...
    開封第一講書人閱讀 51,521評(píng)論 1 304
  • 那天,我揣著相機(jī)與錄音吏恭,去河邊找鬼拗小。 笑死,一個(gè)胖子當(dāng)著我的面吹牛砸泛,可吹牛的內(nèi)容都是我干的十籍。 我是一名探鬼主播蛆封,決...
    沈念sama閱讀 40,288評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼勾栗!你這毒婦竟也來了惨篱?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,200評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤围俘,失蹤者是張志新(化名)和其女友劉穎砸讳,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體界牡,經(jīng)...
    沈念sama閱讀 45,644評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡簿寂,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,837評(píng)論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了宿亡。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片常遂。...
    茶點(diǎn)故事閱讀 39,953評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖挽荠,靈堂內(nèi)的尸體忽然破棺而出克胳,到底是詐尸還是另有隱情,我是刑警寧澤圈匆,帶...
    沈念sama閱讀 35,673評(píng)論 5 346
  • 正文 年R本政府宣布漠另,位于F島的核電站,受9級(jí)特大地震影響跃赚,放射性物質(zhì)發(fā)生泄漏笆搓。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,281評(píng)論 3 329
  • 文/蒙蒙 一纬傲、第九天 我趴在偏房一處隱蔽的房頂上張望满败。 院中可真熱鬧,春花似錦嘹锁、人聲如沸葫录。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,889評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至骇扇,卻和暖如春摔竿,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背少孝。 一陣腳步聲響...
    開封第一講書人閱讀 33,011評(píng)論 1 269
  • 我被黑心中介騙來泰國打工继低, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人稍走。 一個(gè)月前我還...
    沈念sama閱讀 48,119評(píng)論 3 370
  • 正文 我出身青樓袁翁,卻偏偏與公主長(zhǎng)得像柴底,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子粱胜,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,901評(píng)論 2 355

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

  • Spring Cloud為開發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見模式的工具(例如配置管理柄驻,服務(wù)發(fā)現(xiàn),斷路器焙压,智...
    卡卡羅2017閱讀 134,656評(píng)論 18 139
  • 從三月份找實(shí)習(xí)到現(xiàn)在鸿脓,面了一些公司,掛了不少涯曲,但最終還是拿到小米野哭、百度、阿里幻件、京東拨黔、新浪、CVTE绰沥、樂視家的研發(fā)崗...
    時(shí)芥藍(lán)閱讀 42,246評(píng)論 11 349
  • iOS網(wǎng)絡(luò)架構(gòu)討論梳理整理中蓉驹。。揪利。 其實(shí)如果沒有APIManager這一層是沒法使用delegate的态兴,畢竟多個(gè)單...
    yhtang閱讀 5,192評(píng)論 1 23
  • 一甜刻、選擇你的出生 1绍撞、你有個(gè)很有錢的爹,但是你的身體很差但不至于死 2得院、你很窮但是身體很好傻铣,是一夜十次郎的那種 二...
    孤葉南飛閱讀 829評(píng)論 0 4
  • 朋友在平安保險(xiǎn)工作,托我?guī)兔o新產(chǎn)品寫首詩宣傳祥绞,不知道哪來的靈感非洲,還真的寫出來了,與大家分享蜕径! 保險(xiǎn)的名字叫璽越人...
    天佑_f901閱讀 165評(píng)論 0 1