遇到的问题点 flask项目里面的装饰器处理权限验证 java里面好像也是靠装饰器来处理该问题
def permission_required(permission):
def decorator(f):
@wraps(f)
def decorated_function(*args, *kwargs):
if not current_user.can(permission):
abort(403)
return f(args, **kwargs)
return decorated_function
return decorator
def admin_required(f):
return permission_required(Permission.ADMIN)(f)
问题解决过程 写一个简单的装饰器 再解析上面的函数干来上面 总结装饰器
装饰器
廖老师博客:
由于函数也是一个对象,而且函数对象可以被赋值给变量,所以,通过变量也能调用该函数。
def now():
print '2013-12-25'
f = now
f()
2013-12-25
现在,假设我们要增强now()函数的功能,比如,在函数调用前后自动打印日志,但又不希望修改now()函数的定义,这种在代码运行期间动态增加功能的方式,称之为“装饰器”(Decorator)
上面这句话这样理解,我的一个函数处理显示列表的功能,但是我不希望把确认用户是否有阅读该列表的权限这个功能加到该函数中,而我又需要有这种功能,这种在代码运行期间动态增加功能的方式,称之为“装饰器”(Decorator)
#coding=utf-8
from datetime import datetime
def log(func):
def decorator(*args, **kw):
print "log is print"
return func(*args, **kw)
return decorator
@log
def now():
time = datetime.now()
print time.strftime('%Y-%m-%d')
# 等价于 now = log(now)
now()
最简单的实现 别问@ 好像是语法糖 再问确实不清楚
优化下上面
#coding=utf-8
from datetime import datetime
def log(func):
def decorator(*args, **kw):
print "log is print"
print args
print kw
kw['c']()
return func(*args, **kw)
return decorator
@log
def now(*args, **kw):
time = datetime.now()
print time.strftime('%Y-%m-%d')
# 等价于 now = log(now)
def test():
print "me me me"
now('a','b',test,a=1,b=2,c=test)
输出结果
log is print
('a', 'b', <function test at 0x0000000002BF6518>)
{'a': 1, 'c': <function test at 0x0000000002BF6518>, 'b': 2}
me me me
2018-12-10
now 和 他的参赛被传递到log中 decorator 获取来now到参数 ,可以使用,也可以不用,最后返回来now() 方法 这种写法并未改变now函数中任何执行过程,但是先行获取来弄完到参数,并能决定是否执行弄完函数
-- 如果不清楚*args, **kw到用法,建议先行百度 -- 233
但很明显 最上面但问题是三阶但嵌套 作用的范围:
如果decorator本身需要传入参数,那就需要编写一个返回decorator的高阶函数,写出来会更复杂。比如,要自定义log的文本:
def log(text):
def decorator(func):
def wrapper(*args, *kw):
print '%s %s():' % (text, func.name)
return func(args, **kw)
return wrapper
return decorator
@log('execute')
def now():
print '2013-12-25'
之前外层是直接传入函数的 也就没办法在log里面放内容 三阶的写法 等同 now = log('execute')(now)
@permission_required('permission') 'permission' 是权限名称 如果没有特定权限 返回403
最后的问题 @wraps(f) 和 from functools import wraps 含义是什么