jwt

一、jwt认证介绍

1、在用户注册或登录后,我们想记录用户的登录状态,或者为用户创建身份认证的凭证。我们不再使用Session认证机制,而使用Json Web Token(本质就是token)认证机制。
2、用户只要登陆了,返回用户一个token串(随机字符串),每次用户发请求,需要携带这个串过来,验证通过,我们认为用户登陆了
3、JWT的构成(字符串)
由三部分构成(每一部分中间通过 . 分割):header、payload、signature
header:明类型,这里是jwt,声明加密算法,头里加入公司信息等,用base64转码

{
    'typ': 'JWT',
    'alg': 'HS256'
 }

payload:荷载,放着当前用户的信息(用户名,id,token的过期时间,手机号),用base64转码

{
          "sub": "1234567898",
          "name": "egon",
          "admin": true,
          "userid":1,
          'mobile':123444444
        }

signature:签名,这个部分需要base64加密后的header和base64加密后的payload使用.连接组成的字符串,然后通过header中声明的加密方式进行加盐secret组合加密,然后就构成了jwt的第三部分。

**jwt总的构成样子(字符串)**:eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ

4、JWT认证原理:用户携带用户名,密码登陆我的系统,校验通过,生成一个token(三部分),返回给用户,登陆功能完成
访问需要登陆的接口(用户中心),必须携带token过来,后端拿到token后,把header和payload截出来,再通过一样的加密方式和密码得到一个signature,和该token的signature比较,如果一样,表示是正常的token,就可以继续往后访问

二、base64介绍和使用

1、任何语言都有base64的加码和解码,转码方式(加密方式)
2、python中的base64的加密与解密

import base64,json,hashlib
header = {'type':'JWT','alg':'md5'}
payload = {'sub':'123456','name':'egon'}
#header转成json格式字符串再加密
header_str = json.dumps(header)
base64_header = base64.b64encode(header_str.encode('utf-8'))
print(base64_header)   #b'eyJ0eXBlIjogIkpXVCIsICJhbGciOiAibWQ1In0='
#payload加密
payload_str = json.dumps(payload)
base64_payload = base64.b64encode(payload_str.encode('utf-8'))
print(base64_payload)  #b'eyJzdWIiOiAiMTIzNDU2IiwgIm5hbWUiOiAiZWdvbiJ9'

#signature是将header和payload加密后的字符串通过点好相加再进行其他加密方式加密
signature_str = 'eyJ0eXBlIjogIkpXVCIsICJhbGciOiAibWQ1In0='+'.'+'eyJzdWIiOiAiMTIzNDU2IiwgIm5hbWUiOiAiZWdvbiJ9'

signature_hs = hashlib.md5('secret'.encode())
signature_hs.update(signature_str.encode())
res = signature_hs.hexdigest()
print(res)   #7bdb676a1acda6d33a4ec163073769bf

三、jwt基本使用(jwt内置,控制用户登陆后能访问和未登录能访问)

1、drf中使用jwt,借助第三方模块
https://github.com/jpadilla/django-rest-framework-jwt
2、导入:pip3 install djangorestframework-jwt
3、快速使用(默认使用auth的user表)

#1、在默认auth的user表中创建一个用户
#2、在路由中配置
from rest_framework_jwt.views import obtain_jwt_token
path('login/',obtain_jwt_token),
#3、用postman向这个地址发送post请求,携带用户名、密码、登陆成功就会返回token
#4、obtain_jwt_token本质也是一个视图类,继承了APIView
-通过前端传入的用户名密码,校验用户,校验通过,生成token返回
-校验失败返回错误信息

4、用户登陆以后才能访问某个接口

#jwt模块内置了认证类,拿过来局部配置就可以
class OrderView(APIView):
    authentication_classes = [JSONWebTokenAuthentication,]
    # authentication_classes = [myauth.JwtAuthentication,]
    # permission_classes = [IsAuthenticated,]   # 需要搭配一个权限类,用户登陆才能访问,未登陆不能访问
    def get(self,request):
        print(request.user.username)
        return Response('订单的数据')

5、如果用户携带了token,并且配置authentication_classes = [JSONWebTokenAuthentication, ]
,从request.user就能拿到当前登陆用户,如果没有携带token,当前登陆用户就是匿名用户
7、前端要发送请求,携带jwt,格式必须如下

把token放到请求中,key:Authorization 
value:jwt 
eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjo1LCJ1c2VybmFtZSI6ImVnb24xIiwiZXhwIjoxNjA1MjQxMDQzLCJlbWFpbCI6IiJ9.7Y3PQM0imuSBc8CUe_h-Oj-2stdyzXb_U-TEw-F82WE

四、控制登陆接口返回的数据格式

1、控制登陆接口返回的数据格式如下

{
    "code": 100,
    "msg": "登陆成功",
    "token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJ1c2VyX2lkIjoxLCJ1c2VybmFtZSI6ImVnb24iLCJleHAiOjE2MDUzNDUwNjgsImVtYWlsIjoiIn0.FeZ70q8ZKUSSMFPCMHBnHCN_BO7kBAHx6uyRw2cfS0E",
    "user": {
        "username": "egon",
        "icon": "/media/head/default.jpg"
    }
}

2、写一个函数

from app01.serializer import ReadonlyModelSerializer
def jwt_response_payload_handler(token,user=None,request=None):
    return {
        'code':100,
        'msg':'登陆成功',
        'token':token,
        'user':ReadonlyModelSerializer(instance=user).data
    }

3、在settings.py中配置

JWT_AUTH = {
    'JWT_RESPONSE_PAYLOAD_HANDLER': 'app01.utils.jwt_response_payload_handler',
}

五、自定义基于jwt的认证类

要求:自己实现基于jwt的认证类,通过认证,才能继续访问,通不过认证就返回错误

#在项目文件夹下新建一个myauth.py文件
from rest_framework.exceptions import AuthenticationFailed
from rest_framework_jwt.authentication import BaseJSONWebTokenAuthentication, jwt_decode_handler
from rest_framework_jwt.utils import jwt_decode_handler
import jwt
class JwtAuthentication(BaseJSONWebTokenAuthentication):
    def authenticate(self, request):
        print(request.META)
        token = request.META.get('HTTP_Authorization'.upper())
        try:
            payload = jwt_decode_handler(token)
        except jwt.ExpiredSignature:
            raise AuthenticationFailed('过期了')
        except jwt.DecodeError:
            raise AuthenticationFailed('解码错误')
        except jwt.InvalidTokenError:
            raise AuthenticationFailed('不合法的token')
        user = self.authenticate_credentials(payload)
        return (user,token)
#在视图类中配置
authentication_classes = [myauth.JwtAuthentication,]
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 222,183评论 6 516
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 94,850评论 3 399
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 168,766评论 0 361
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 59,854评论 1 299
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 68,871评论 6 398
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 52,457评论 1 311
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,999评论 3 422
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,914评论 0 277
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 46,465评论 1 319
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 38,543评论 3 342
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 40,675评论 1 353
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 36,354评论 5 351
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 42,029评论 3 335
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 32,514评论 0 25
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,616评论 1 274
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 49,091评论 3 378
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 45,685评论 2 360

推荐阅读更多精彩内容

  • 好久没写博客了,因为最近公司要求我学spring cloud,早点将以前软件迁移到新的架构上。所以我那个拼命的学呐...
    tengshe789阅读 4,166评论 1 11
  • Json web token(JWT)是为了网络应用环境间传递声明而执行的一种基于JSON的开发标准(RFC 75...
    YU_XI阅读 7,529评论 0 4
  • Lesson-1 Session Session是什么 其实就是用户的认证与授权。认证与授权又是什么?认证,就是让...
    羽晞yose阅读 1,202评论 0 1
  • 久违的晴天,家长会。 家长大会开好到教室时,离放学已经没多少时间了。班主任说已经安排了三个家长分享经验。 放学铃声...
    飘雪儿5阅读 7,528评论 16 22
  • 创业是很多人的梦想,多少人为了理想和不甘选择了创业来实现自我价值,我就是其中一个。 创业后,我由女人变成了超人,什...
    亦宝宝阅读 1,818评论 4 1