我最近也一直在玩装饰者,我的印象是没有一个好的方法来做到这一点。您不能从函数外部访问函数的本地范围。
一个潜在的解决方案,虽然不正是你想要的,使用部分函数应用和函数成员的数据可能是:
from functools import wraps
schema = { 'lang': {'type': 'string', 'required':True} }
def compare(schema, json):
return schema == json
def validate(schema):
def outer(function):
@wraps(function)
def inner(*args, **kwargs):
return function(*args, **kwargs)
inner.validate = lambda json: compare(schema, json)
return inner
return outer
@validate(schema)
def main_function():
print main_function.validate({ 'lang': {'type': 'string', 'required':True} })
print main_function.validate({})
main_function()
# Output:
# True
# False
的compare
功能可以显着客户要求做一些有用的东西,但你仍然需要从main_function
验证json。我不知道在main_function
范围内是否有解决方法,而没有制定内部功能。
也可能“注入”变量到一个函数的全球范围和使用装饰做必要的簿记:
from functools import wraps
schema = {
'lang': {'type': 'string', 'required':True}
}
def validate(schema):
def my_decorator(func):
@wraps(func)
def wrapper(*args, **kwargs):
_backup, _check = None, False
if 'valid_json' in func.func_globals:
_backup, _check = func.func_globals['valid_json'], True
valid_json = {'hi': 'mom'} # or whatever
func.func_globals['valid_json'] = valid_json
output = func(*args, **kwargs)
if _check:
func.func_globals['valid_json'] = _backup
else:
del func.func_globals['valid_json']
return output
return wrapper
return my_decorator
@validate(schema)
def main_function():
print valid_json
main_function()
# Output:
# {'hi': 'mom'}
是否可以让你想如何你的装饰是使用,即你理想的语法? –
@JaredGoguen我编辑了主帖子 –
装饰者中的“body”是什么?为什么'wrapper'在某个时候不会调用'func'? – Blckknght