python-fire
python-fire copied to clipboard
Could be cool and likely easy to add optional typechecking from annotations with Typeguard
Typeguard https://github.com/agronholm/typeguard makes it very easy to add annotation-based type checking that uses the full gamut of what typing
offers, with just a decorator, for example.
Using the type checking decorator with Fire is very cool, but I feel like it would be even better if Fire used it internally to display a more user-friendly message to the user when they give an input that doesn't fit the type of the annotation.
Thanks.
@dbieber
FWIW, I tend to use the following custom decorator to get this behavior:
import functools
import inspect
import typeguard
def typechecked(func):
__annotations__ = getattr(func, '__annotations__', None)
if __annotations__:
__signature__ = inspect.signature(func)
@functools.wraps(func)
def wrapper(*args, **kwargs):
try:
return typeguard.typechecked(func)(*args, **kwargs)
except TypeError as exc:
err = str(exc)
found = False
for param in __signature__.parameters.values():
if f'type of argument "{param.name}" ' not in err:
continue
found = True
if param.kind == param.POSITIONAL_ONLY or param.default == param.empty:
err = err.replace(param.name, param.name.upper())
elif param.kind in {param.POSITIONAL_OR_KEYWORD, param.KEYWORD_ONLY}:
err = err.replace(param.name, f"--{param.name.replace('_', '-')}")
if found:
raise fire.core.FireError(err)
raise exc
return wrapper
return func
Example:
@typechecked
def foo(n: int):
for i in range(n):
print(i)
fire.Fire(foo)
That's great -- thanks for sharing that @melsabagh-kw!
You can try afire, which is a fork of python-fire supporing type convert according to the type hint.
You can try afire, which is a fork of python-fire supporing type convert according to the type hint.
I created an issue on afire as well, but @zqqqqz2000 , is there any plan to merge this work back into Fire or is there some technical reason why it needs to stay separate?