Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

When a type error results from type information being lost because an object (context manager) is used with with (with-as block), mypy should emit a hint alluding to this. #17086

Open
wyattscarpenter opened this issue Apr 2, 2024 · 2 comments
Labels

Comments

@wyattscarpenter
Copy link
Contributor

Feature

When a type error results from type information being lost because an object (context manager) is used with with (with-as block), mypy should emit a hint alluding to this.

Pitch

Consider the following issue, which is not by me but is a predicament I also ran into recently:

#9750

The user is, essentially, confused why the type of x.y is int but the type of c.y in with x as c: c.y is Any.

This happens because the __enter__ method of x is missing a return type signature, so mypy treats its output as having type Any. However, it is a common (as fair as I can tell) pattern for an object's __enter__ method to simply return self — possibly without a proper type signature, thus wiping its type information in the process. So, I think this would be a useful hint for mypy to emit, if it encounters any type problems where the problematic value has just resulted from a with statement.

Something like: hint: the type of c.y is Any, but the type of x is Foo. Did you mean the type of c to be Foo? If so, add the return type annotation -> Self to the __enter__ method of Foo.

Currently, there is no warning about this whatsoever, which means in the (admittedly, rare) circumstances where this problem crops up, it is unintuitive and the user has very little to go off of.

@pbodnar
Copy link

pbodnar commented Aug 19, 2024

+1 I've just run into this issue as well. Interestingly, Pylance (used by my VS Code) infers the expected type on its own, i.e. without any annotation needed on the __enter__ method. At minimum for the case of with Renderer() as renderer: ... (with Renderer.__enter__ implemented as return self). Wondering if mypy couldn't do the same...

@wyattscarpenter
Copy link
Contributor Author

Presumably the difference between mypy and pyright here is a result of the general difference in unannotated inference strategies described in, eg, https://github.com/microsoft/pyright/blob/main/docs/mypy-comparison.md#inferred-return-types :

If a function or method lacks a return type annotation, pyright infers the return type from return and yield statements within the function’s body (including the implied return None at the end of the function body). This is important for supporting completion suggestions. It also improves type checking coverage and eliminates the need for developers to needlessly supply return type annotations for trivial return types.

By comparison, mypy never infers return types and assumes that functions without a return type annotation have a return type of Any. This was an intentional design decision by mypy developers and is explained in this thread.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants