Passing parameters to enable/disable decorators from different scripts

46 Views Asked by At

I would like to disable my decorator when I execute a function from another script

Following the documentation from the wrapt module, here is my simple decorator and function:

# script_1.py

import wrapt

def _enabled():
    return True

@wrapt.decorator(enabled=_enabled)
def my_decorator(wrapped, instance, args, kwargs):
    print('decorator enabled')
    return wrapped(*args, **kwargs)

@my_decorator
def my_function():
    print('function enabled')
    pass

If I then call my_function() I will get this result:

>>> my_function()
decorator enabled
function enabled
>>>  

However, I would like to toggle the disable/enable functionality from another script, as such:

# script_2.py

from main import my_function

# somehow pass 'False' to the decorator and therefore suppress the the print.
my_function() 

In order to get this result:

>>> my_function()
function enabled
>>>  
2

There are 2 best solutions below

0
chepner On

Your _enabled function needs to access some variable whose value you can change, rather than hard-coding its return value.

_foo = True

def _enabled():
    return _foo

@wrapt.decorator(enabled=_enabled)
def my_decorator(wrapped, instance, args, kwargs):
    print('decorator enabled')
    return wrapped(*args, **kwargs)

@my_decorator
def my_function():
    print('function enabled')

Now you can modify the value of script1._foo before calling my_function.

>>> import main
>>> from main import my_function
>>> my_function()
decorator enabled
function enabled
>>> main._foo = False
>>> my_function()
function enabled
0
Magaren On

You can use sys to do the job:

script_1.py

import wrapt
import sys

def _enabled():
    return not "script_1" in sys.modules

@wrapt.decorator(enabled=_enabled)
def my_decorator(wrapped, instance, args, kwargs):
    print('decorator enabled') if _enabled() else ""
    return wrapped(*args, **kwargs)

@my_decorator
def my_function():
    print("function enabled")

if __name__ == '__main__':
    my_function()

script_2.py

from script_1 import my_function

if __name__ == '__main__':
    my_function()