【问题标题】:How parameters pass in decorator of python?参数如何传入python的装饰器?
【发布时间】:2013-11-03 09:53:43
【问题描述】:
def require(role):
    def wrapper(fn):
         def new_fn(*args, **kwargs):
             if not role in kwargs.get('roles', []):
                 print("%s not in %s" % (role, kwargs.get('roles', [])))
                 raise Exception("Unauthorized")
             return fn(*args, **kwargs)
         return new_fn
    return wrapper

@require('admin')
def get_users(**kwargs):
    return ('Alice', 'Bob')

以上代码将装饰器require 参数化为admin。看来函数get_users 传递给wrapper 的参数fn。但是,get_users 是如何传递给参数fn 的呢?

【问题讨论】:

  • 你的意思是你想让get_users() 也访问role 值?

标签: python closures decorator


【解决方案1】:

当一个函数在另一个函数中定义时,就像这里发生的那样(实际上,这里有两个层次的 this),内部函数可以访问所有外部函数的变量。因此没有必要将rolefn 显式传递给内部函数。

这是发生了什么:

  1. 调用require() 时将role 设置为"admin"
  2. require() 函数定义了另一个函数 wrapper(),它返回。 (顺便说一句,这个函数的名字并不好:它是进行包装的函数,而不是实际用作包装器的函数。它可能应该称为wrap()decorate()。)
  3. wrapper() 被传递给函数get_users()
  4. wrapper() 创建了一个新函数new_fn(),以代替 get_users() 调用,并返回new_fn()。 (同样,这不是最好的名字,它可能应该被称为wrapper(),因为它是被装饰函数的包装器。)

现在,由于前面提到的情况,内部函数可以访问所有外部函数的变量(称为“闭包”),new_fn() 可以访问 fn,这是它包装的函数(@987654339 @) 以及最初传递给require()role 参数。因此它可以检查用户的角色以查看是否允许用户调用该函数,然后,如果允许,则调用该函数并返回结果,从而作为 get_users() 的替代品,并在原始函数周围添加了功能.

【讨论】:

  • 我知道没有必要将角色或 fn 显式传递给内部函数。我对传递给内部函数的 fn 没有明确的含义感到困惑。
  • 我真的不知道你在问什么。
【解决方案2】:

这里get_users()没有传递参数fn

因为函数get_users()绑定到装饰器require

所以首先调用装饰器,而 get_users() 的对象/引用作为参数传递

详情请参考https://wiki.python.org/moin/PythonDecorators

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-04-13
    • 2012-04-27
    • 2018-05-30
    • 2021-03-20
    • 2014-07-21
    相关资源
    最近更新 更多