I have three python functions:
def decorator_function(func)
def wrapper(..)
return func(*args, **kwargs)
return wrapper
def plain_func(...)
@decorator_func
def wrapped_func(....)
inside a module A.
Now I want to get all the functions inside this module A, for which I do:
for fname, func in inspect.getmembers(A, inspect.isfunction):
# My code
The problem here is that the value of func is not what I want it to be.
It would be decorator_function, plain_func and wrapper (instead of wrapped_func).
How can I make sure that wrapped_func is returned instead of wrapper?
You can access the pre-decorated function with:
wrapped_func.func_closure[0].cell_contents()
For example,
def decorator_function(func):
def wrapper(*args, **kwargs):
print('Bar')
return func(*args, **kwargs)
return wrapper
@decorator_function
def wrapped_func():
print('Foo')
wrapped_func.func_closure[0].cell_contents()
prints
Foo # Note, `Bar` was not also printed
But really, if you know you want to access the pre-decorated function, then it would be a whole lot cleaner to define
def wrapped_func():
print('Foo')
deco_wrapped_func = decorator_function(wrapped_func)
So wrapped_func
will be the pre-decorated function, and
deco_wrapped_func
will be the decorated version.
If all you want is to keep the original function name visible from "the outside" I think that you can do that with
@functools.wraps
as a decorator to your decorator
here's the example from the standard docs
>>> 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()
Calling decorated function
Called example function
>>> example.__name__
'example'
>>> example.__doc__
'Docstring'
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With