Python中的 装饰器

在阐述什么是装饰器前,我们先来说一下什么是闭包

闭包:

  1. 在一个外函数中 定义了一个内函数
  2. 内函数运用了 外函数的临时变量
  3. 外函数的返回值 是内函数的引用
 def outer( ):   
        a=100    
        def inner( ):    
              b=a+100    
              print(b)    
        return inner    
 outer( )( )     

装饰器:

以@开头,装饰器是在函数调用之上的修饰器,在不改变项目原有代码的基础上,增加一些额外的功能

装饰器使用场景
授权:装饰器能有助于检查某个人是否被授权去使用一个web应用的端点(endpoint)。它们被大量使用于Flask和Django web框架中
日志:在记录日志的地方添加装饰器
缓存:通过装饰器获取缓存中的值

函数装饰器

一个装饰器:

def outer(func):   
	def inner(a,b) / def inner( *args,**kwargs):   
		print("特殊效验功能的执行")   
		func(a,b) / func( *args,**kwargs)   
		print("停止执行")   
	return inner   
	 
	@outer   
	def f(a,b):    
		print("a+b=",(a+b))    
	f(10,20)     
  	# 输出结果: 
	特殊效验功能的执行
	30
	停止执行

多个装饰器:
开始: 自上而下
结束: 自下而上

def outer1(func):   
	def inner(a,b) / def inner( *args,**kwargs):   
		print("特殊效验功能 1 的执行")   
		print("111111111111")
		func(a,b) / func( *args,**kwargs)   
		print("1 停止执行")     
		print("111111111111")  
	return inner    

def outer2(func):    
	def inner(a,b) / def inner( *args,**kwargs):       
		print("特殊效验功能 2 的执行")      
		print("222222222222")      
		func(a,b) / func( *args,**kwargs)      
		print("2 停止执行")       
		print("222222222222")        
	return inner          
  @outer1        
  @outer2        
  def f(a,b):            
      print("a+b=",(a+b))          
  f(10,20)         
  #输出结果: 特殊功能效验 1 的执行
                   111111111111
                   特殊功能效验 2 的执行
                   222222222222
                   30
                   2 停止执行
                   222222222222
                   1 停止执行
                   111111111111

类装饰器的运用

这里的代码,展示的是 jwt 和 类装饰的结合使用

目的: 防止用户 使用他人敏感信息 进行篡改
import jwt

#装饰器
def my_decorator(func):
    def wrapper(request,*args,**kwargs):
        print('这个装饰器被调用了')
        print('请求接口地址是%s' % request.path)
        #判断jwt逻辑
        uid = request.GET.get("uid")
        clinet_jwt = request.GET.get("jwt",None)
        if clinet_jwt is None:
            return HttpResponse('没有令牌')
        decode_jwt = jwt.decode(clinet_jwt,'123',algorithms=['HS256'])
        if decode_jwt['uid'] != str(uid):
            return HttpResponse('你篡改了用户id')
        return func(request,*args,**kwargs)
    return wrapper
#类装饰器调用
from django.utils.decorators import method_decorator

在查询用户信息类时  调用
#用户信息
class UserInfo(APIView):
    @method_decorator(my_decorator)
    def get(self,request):
        uid = request.GET.get('uid')
        #查询数据
        user = User.objects.get(id=int(uid))
        #序列化对象
        user_ser = UserSer(user)
        return Response(user_ser.data)

在 用户登录接口  后端
#登录接口
class Login(APIView):
    def get(self,request):
        #接收参数
        username = request.GET.get('username','没有接受到')
        password = request.GET.get('password','没有接受到')
        #查询数据
        user = User.objects.filter(username=username,password=make_password(password)).first()
        if user:
            res = {
     }
            res['code'] = 200
            res['message'] = '登录成功'
            res['username'] = user.username
            res['uid'] = user.id
            #加入jwt 编码机制
            #进行编码
            encode_jwt = jwt.encode({
     'uid':str(user.id)},'123',algorithm='HS256')
            #解码操作
            #强转
            encode_str = encode_jwt.decode('utf-8')
            res['jwt'] = encode_str
            return Response(res)
        else:
            res = {
     }
            res['code'] = 405
            res['message'] = '用户名或密码错误'
            return Response(res)

在前端的登录 接口中  要将 jwt 存储到  localStorage 里面
localStorage.setItem('jwt',result.data.jwt)

你可能感兴趣的:(python)