Search code examples
pythondecoratormypypython-typing

Decorated function return type remains original when called directly


Defining a decorator that takes Callable[..., int] and returns Callable[..., str] seems to not be understood by mypy

def decorator(wrapped: Callable[..., int]) -> Callable[..., str]:
    def wrapper() -> str:
        return str(wrapped())

    return wrapper


@decorator
def foo() -> int:
    return 0


def bar():
    x = foo()  # mypy sees x as int even though the decorator(foo)() returns str

Is there something I can do, so that the return type of foo() is not its original return type, but the return type specified by the decorator?

Edit: Simplified the example


Solution

  • This is what i see in last version of mypy (0.930): str not int

    def decorator(wrapped: Callable[..., int]) -> Callable[..., str]:
    
        def wrapper() -> str:
            return str(wrapped())
    
        return wrapper
    
    
    @decorator
    def foo() -> int:
        return 0
    
    
    def bar() -> None:
        x = foo()
        reveal_type(x)  # Mypy: Revealed type is "builtins.str"