Skip to content

[stubtest] Stubtest reports incorrect argument name errors for overloads with positional only arguments #16956

Open
@Daverball

Description

@Daverball

Bug Report

Sometimes functions are overloaded in a way where the same positional argument (usually the very first one) is reused for different kinds of objects, affecting the outcome. So for documentation purposes it can be nice to give that argument a different name depending on the overload. As long as that argument is positional-only and that particular overload doesn't also take **kwargs, the name of the argument should be ignored when matching against the original function signature, as long as the argument matches positionally, that should be good enough, there's only a safety issue if you can also pass the same argument by name in that overload.

To Reproduce

Source:

def foo(name_or_number): ...

Stub:

@overload
def foo(number: int, /): ...
@overload
def foo(name_or_number: str): ...

Expected Behavior

stubtest is fine with accepting the first overload as a possibility

Actual Behavior

It looks like when you do that, stubtest will complain on the first overload, since there's no number argument, and then also complain on the second overload, because it will now infer that the original function must look like def foo(number: int = ..., number_or_number: str = ...) for some reason

error: [...].foo is inconsistent, stub argument "number" differs from runtime argument "text_or_number"
Stub: in file [...]
Overload(def (number: int) -> Any, def(name_or_number: str) -> Any)
Inferred signature: def (number: int = ..., name_or_number: str = ...)
Runtime: in file [...]
def (name_or_number) -> Any

error: [...].foo is inconsistent, stub argument "number" has a default value but runtime argument does not
Stub: in file [...]
Overload(def (number: int) -> Any, def(name_or_number: str) -> Any)
Inferred signature: def (number: int = ..., name_or_number: str = ...)
Runtime: in file [...]
def (name_or_number) -> Any

error: [...].foo is inconsistent, runtime does not have argument "name_or_number"
Stub: in file [...]
Overload(def (number: int) -> Any, def(name_or_number: str) -> Any)
Inferred signature: def (number: int = ..., name_or_number: str = ...)
Runtime: in file [...]
def (name_or_number) -> Any

Found 3 errors (checked 1 modules)

Your Environment

  • Mypy version used: 1.8.0
  • Mypy command-line flags: --ignore-missing-stub
  • Mypy configuration options from mypy.ini (and other config files):
  • Python version used: 3.10

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions