I would like to define a decorator with a parameter that raises an error if the parameter is missing.
Here's a naive attempt on a simplified example:
def decorator_with_arg(a=None):
if a is None :
raise ValueError("Missing argument in decorator")
def decorator(func):
def wrapped_func(x):
return func(x+ a)
return wrapped_func
return decorator
But when I use this decorator without a parameter it's not raising any errors:
@decorator_with_arg
def simple_func(x):
return 2*x
simple_func(1)
How can I raise an exception?
You are not using your decorator correctly, in your code simple_func(1)
will just return wrapped_func
, because @decorator_with_arg
will simply do:
simple_func = decorator_with_arg(simple_func)
# ^ this is passing a=simple_func
# now simple_func is the decorator function defined inside decorator_with_arg
You need to call your decorator_with_arg
in order for it to return decorator
which will then be used to decorate the function:
@decorator_with_arg(100)
def simple_func(x):
return 2*x
print(simple_func(1)) # 202
In any case, if you want to make an argument mandatory, simply declare it without a default value:
def decorator_with_arg(a):
# ...
And remove the if a is None
check.
If you want to avoid mistakes in using @decorator_with_arg
instead of @decorator_with_arg()
, you can add a check to ensure a
is not a function:
def decorator_with_arg(a):
if callable(a):
raise TypeError("Incorrect use of decorator")
def decorator(func):
def wrapped_func(x):
return func(x + a)
return wrapped_func
return decorator
@decorator_with_arg
def func():
return 1
# TypeError: Incorrect use of decorator
@decorator_with_arg(123)
def func():
return 1
# All fine