functools.wraps behaviour

ISE Development isenntp at gmail.com
Mon Sep 15 19:15:05 EDT 2014


The purpose of 'functools.wraps' is to make a decorated function look like 
the original function, i.e. such that the __name__, __module__, __doc__ 
attributes are the same as the wrapped function.

However, I've noticed inconsistent behaviour.

Given the following:

    import functools

    def decorator(func):
        @functools.wraps(func)
        def wrapper(self):
            func(self)
        return wrapper

    class Klass:
        @decorator
        def method(self):
            raise Exception('boom!')

    print('Klass.method:',Klass.method)

    k = Klass()
    print('k.method',k.method)

    try:
        k.method(1)
    except Exception as e:
        print('exception:',e)

The output (Python 3.3) is:

Klass.method: <function Klass.method at 0x7f2d7c454b00>
k.method <bound method Klass.method of <__main__.Klass object at 
0x7f2d7c4570d0>>
exception: wrapper() takes 1 positional argument but 2 were given

The first two lines are as expected, using the name of the decorated 
function. However, the exception uses the name of the decorating wrapper 
function.

Is this a bug in functools? Or is this a language feature? If so, is there a 
valid argument to change this behaviour?

-- isedev



More information about the Python-list mailing list