使用django開發(fā)微信小程序后端

tips: 本文面向的對象是已經(jīng)會使用django開發(fā)web后端的人員

微信小程序后端與普通web的區(qū)別

微信小程序的后端開發(fā)和普通的restful API 大致上相同侮腹,只不過要注意以下幾點限制

  • 必須使用HTTPS協(xié)議請求后端服務(wù)器
  • 不支持COOKIE
  • 不支持django內(nèi)置的user登錄, 因為它使用的是微信的用戶系統(tǒng)

應(yīng)對方法

  • 對于HTTPS的限制, 很簡單, 去godaddy等網(wǎng)站申請一個https證書, 下載后使用nginx指定即可, 可以參照此文章, 這篇文章的證書是自己生成的, 這里需要替換為申請的證書

  • 不支持cookie, django原生的session機制就會失效

  • 不支持django內(nèi)置的user登錄, 因為它使用的是微信的用戶系統(tǒng)

    對于上邊這兩個問題,我使用了JWT來保證了用戶的在線驗證. 那么什么是JWT呢, 可以看下推酷的這篇文章了解一下, 簡要的來說就是用戶登錄以后, 原先保存在cookie里邊的一個隨機的sessionid變成了保存在http頭部的Authorization字段的一個token值, 這個值是服務(wù)端自身加密的, 客戶端無需解密, 只要服務(wù)端知道這個token對應(yīng)這個用戶就好, 當(dāng)然這里也有很多的附加功能, 比如超時等等, 不再贅述

    然而網(wǎng)上有很多的jwt開源項目, 比如django-jwt, rest-framework-jwt, 你都可以使用, 但是卻不適用于微信小程序, 為什么這么說? 是因為這兩個項目都和django內(nèi)置的user相耦合, 在上邊提出的第三個問題的地方會引起問題, 在嘗試了rest-framework-jwt發(fā)現(xiàn)問題后, 我毅然決定自己使用pyjwt實現(xiàn)一個用戶登錄/鑒權(quán)的組件.

    首先要知道微信小程序的登錄流程是:

    1. 客戶端請求用戶授權(quán)
    2. 用戶授權(quán)成功
    3. 客戶端或得到用戶基本信息(包括code,沒有openid的用戶明文信息, 有openid的加密后的信息, 解密向量iv)
    4. 客戶端把返回的信息發(fā)送到服務(wù)器
    5. 服務(wù)器使用code去微信服務(wù)器換取session_key
    6. 服務(wù)器用這個session_key+iv去解密用戶密文, 得到用戶完整信息(基本+openid)
    7. 將用戶在服務(wù)器登錄, 維持用戶session(這里的失效時間微信約定是30天)

看起來好像步驟很多, 但是我們沒有必要去重新造輪子, 早有人已經(jīng)寫好認證流程python-weixin我們可以省去4-6的步驟, 那么剩下的問題就是如何解決第7步也就是維持session的問題了.

因為jwt始終使用http頭部的token進行驗證這里我的思路是:

  1. 微信用戶登錄后, 返回客戶端token, 并在緩存創(chuàng)建用戶的session信息
  2. 客戶端請求時附加http頭Authorization=JWT <token>
  3. 使用中間件檢驗http頭的token, 審查通過則在request上追加一個jwt_user屬性(這里不想覆蓋django自帶user), 同時去緩存尋找這個用戶的session信息, 加載到request.jwt_session, 審查如果不通過則jwt_user設(shè)置為None, jwt_session為一個空的session對象
  4. 使用認證方法, 對于需要進行登錄的接口檢驗用戶是否為None

到這一步就已經(jīng)完成了整個的用戶鑒權(quán)/session持久化流程, 如果你只是為了了解django開發(fā)小程序注意的點到這里已經(jīng)可以結(jié)束了, 下邊我要介紹的是我實現(xiàn)的一套中間件邏輯, 有興趣可以拿去直接使用.

這里中間件我已經(jīng)實現(xiàn)了參見django-jwt-session-auth, 調(diào)用模塊內(nèi)部的jwt_login函數(shù), 登錄你的用戶時會返回一個token, 這個token將要返回客戶端, 同時它也會做user的session緩存動作.下一次客戶端帶著Authorization=JWT <token>調(diào)用的時候中間件會直接將對應(yīng)的user和session加載到request.jwt_userrequest.jwt_session, 這里你需要設(shè)置的只有設(shè)置兩個值: USER_TO_PAYLOADPAYLOAD_TO_USER兩個方法:
* USER_TO_PAYLOAD: 根據(jù)當(dāng)前登錄的用戶生成一個字典payload方法
* PAYLOAD_TO_USER: 根據(jù)你之前生成的payload找到對應(yīng)的用戶

注: 2017.1.15我這個組件還沒有完整的readme, 后續(xù)會加上

最后, 關(guān)于認證器, 如果你使用rest-framework可以直接繼承BaseAuthenticationauthenticate方法里校驗jwt_user是否為None即可, 如果直接使用django原生的view, 可以寫一個裝飾器裝飾在類view的dispatch方法上或直接裝飾在函數(shù)的view上.

示例

# django-jwt-session-auth設(shè)置, 放在settings.py文件中
JWT_AUTH = {
    'PAYLOAD_TO_USER': 'user.auth.payload_to_user',
    'USER_TO_PAYLOAD': 'user.auth.user_to_payload',
}

# rest-framework驗證器
class WechatUserAuthentication(BaseAuthentication):
    def authenticate(self, request):
        if not request.jwt_user:
            msg = u'請先授權(quán)'
            raise exceptions.AuthenticationFailed(msg)
        return (request.jwt_user, request.jwt_user.uuid)

# 原生django驗證裝飾器
def login_required(func):
    @wraps(func)
    def verify_login(request, *args, **kwargs):
        if request.jwt_user:
            return func(request, *args, **kwargs)
        else:
            # 返回HTTP_401
    return verify_login
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末疗垛,一起剝皮案震驚了整個濱河市爬舰,隨后出現(xiàn)的幾起案子新娜,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 216,544評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異永品,居然都是意外死亡,警方通過查閱死者的電腦和手機击纬,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,430評論 3 392
  • 文/潘曉璐 我一進店門鼎姐,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事炕桨》钩ⅲ” “怎么了?”我有些...
    開封第一講書人閱讀 162,764評論 0 353
  • 文/不壞的土叔 我叫張陵献宫,是天一觀的道長钥平。 經(jīng)常有香客問我,道長姊途,這世上最難降的妖魔是什么涉瘾? 我笑而不...
    開封第一講書人閱讀 58,193評論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮捷兰,結(jié)果婚禮上立叛,老公的妹妹穿的比我還像新娘。我一直安慰自己贡茅,他們只是感情好秘蛇,可當(dāng)我...
    茶點故事閱讀 67,216評論 6 388
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著顶考,像睡著了一般赁还。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上村怪,一...
    開封第一講書人閱讀 51,182評論 1 299
  • 那天秽浇,我揣著相機與錄音浮庐,去河邊找鬼甚负。 笑死,一個胖子當(dāng)著我的面吹牛审残,可吹牛的內(nèi)容都是我干的梭域。 我是一名探鬼主播,決...
    沈念sama閱讀 40,063評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼搅轿,長吁一口氣:“原來是場噩夢啊……” “哼病涨!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起璧坟,我...
    開封第一講書人閱讀 38,917評論 0 274
  • 序言:老撾萬榮一對情侶失蹤既穆,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后雀鹃,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體幻工,經(jīng)...
    沈念sama閱讀 45,329評論 1 310
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,543評論 2 332
  • 正文 我和宋清朗相戀三年黎茎,在試婚紗的時候發(fā)現(xiàn)自己被綠了囊颅。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 39,722評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖踢代,靈堂內(nèi)的尸體忽然破棺而出盲憎,到底是詐尸還是另有隱情,我是刑警寧澤胳挎,帶...
    沈念sama閱讀 35,425評論 5 343
  • 正文 年R本政府宣布饼疙,位于F島的核電站,受9級特大地震影響慕爬,放射性物質(zhì)發(fā)生泄漏宏多。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,019評論 3 326
  • 文/蒙蒙 一澡罚、第九天 我趴在偏房一處隱蔽的房頂上張望伸但。 院中可真熱鬧,春花似錦留搔、人聲如沸更胖。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,671評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽却妨。三九已至,卻和暖如春括眠,著一層夾襖步出監(jiān)牢的瞬間彪标,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,825評論 1 269
  • 我被黑心中介騙來泰國打工掷豺, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留捞烟,地道東北人。 一個月前我還...
    沈念sama閱讀 47,729評論 2 368
  • 正文 我出身青樓当船,卻偏偏與公主長得像题画,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子德频,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 44,614評論 2 353

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