我在 View 函数中使用装饰器(来自 @render_to 包的 django_annoying)。

但问题是我想获取 View 函数返回的原始 dict 用于测试目的,而不是装饰器返回的 HttpResponse 对象。

装饰器使用 @wraps (来自 functools )。

如果无法访问它,那么您知道如何测试它吗?

最佳答案

包装的函数将作为函数闭包单元提供。哪个单元格完全取决于有多少闭包变量。

对于一个简单的包装器,其中唯一的闭包变量是要包装的函数,它将是第一个:

wrapped = decorated.func_closure[0].cell_contents

但您可能必须检查所有 func_closure 值。

使用 functools.wraps() example decorator 的演示:
>>> from functools import wraps
>>> def my_decorator(f):
...     @wraps(f)
...     def wrapper(*args, **kwds):
...         print 'Calling decorated function'
...         return f(*args, **kwds)
...     return wrapper
...
>>> @my_decorator
... def example():
...     """Docstring"""
...     print 'Called example function'
...
>>> example
<function example at 0x107ddfaa0>
>>> example.func_closure
(<cell at 0x107de3d70: function object at 0x107dc3b18>,)
>>> example.func_closure[0].cell_contents
<function example at 0x107dc3b18>
>>> example()
Calling decorated function
Called example function
>>> example.func_closure[0].cell_contents()
Called example function

看看 source code for @render_to 你不必担心这个;包装的函数将存储在第一个闭包槽中,保证。

如果这是 Python 3,则可以使用 __wrapped__ 属性访问包装函数:
>>> example.__wrapped__
<function example at 0x103329050>

如果您可以访问装饰器代码本身,您也可以轻松地在 Python 2 代码中添加相同的引用:
def my_decorator(f):
    @wraps(f)
    def wrapper(*args, **kwds):
        # implementation

    wrapper.__wrapped__ = f
    return wrapper

使内省(introspection)更容易一点。

关于python - 出于测试目的访问原始装饰函数,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/14942282/

10-09 17:10
查看更多