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

Fix callable instance variable support (take 2) #13400

Merged
merged 7 commits into from
Aug 13, 2022

Conversation

ilevkivskyi
Copy link
Member

Fixes #708
Fixes #5485

This builds on the original proposal by @wyfo, but handles three important issues/edge cases:

  • This PR fixes serialization of is_inferred so that the distinction works correctly in incremental mode (I added a test)
  • Dunder operator methods are always considered class variables (this is a relatively common pattern and matches Python semantics; there is an existing tests that previously needed ClassVar[...])
  • If we detect a Too few arguments error for a variable with callable type we give a note suggesting to try ClassVar[...]

I also add a short doc paragraph on this.

cc @JukkaL

@github-actions
Copy link
Contributor

Diff from mypy_primer, showing the effect of this PR on open source code:

graphql-core (https://github.com/graphql-python/graphql-core)
+ src/graphql/execution/execute.py:216: error: Unused "type: ignore" comment
+ src/graphql/execution/execute.py:217: error: Unused "type: ignore" comment
+ src/graphql/execution/execute.py:218: error: Unused "type: ignore" comment
+ src/graphql/execution/execute.py:796: error: Unused "type: ignore" comment

pydantic (https://github.com/samuelcolvin/pydantic)
+ pydantic/validators.py:515: error: Unused "type: ignore" comment

werkzeug (https://github.com/pallets/werkzeug)
+ src/werkzeug/local.py:316: error: Unused "type: ignore" comment

sphinx (https://github.com/sphinx-doc/sphinx)
+ sphinx/domains/std.py: note: In member "handle_signature" of class "GenericObject":
+ sphinx/domains/std.py:49:20: error: Too few arguments  [call-arg]
+ sphinx/domains/std.py:49:20: note: "parse_node" is considered instance variable, to make it class variable use ClassVar[...]
+ sphinx/domains/std.py:49:36: error: Argument 1 has incompatible type "BuildEnvironment"; expected "GenericObject"  [arg-type]
+ sphinx/domains/std.py:49:46: error: Argument 2 has incompatible type "str"; expected "BuildEnvironment"  [arg-type]
+ sphinx/domains/std.py:49:51: error: Argument 3 has incompatible type "desc_signature"; expected "str"  [arg-type]

urllib3 (https://github.com/urllib3/urllib3)
+ src/urllib3/connection.py:237: error: Too few arguments  [call-arg]
+ src/urllib3/connection.py:237: note: "_tunnel" is considered instance variable, to make it class variable use ClassVar[...]

jinja (https://github.com/pallets/jinja)
+ src/jinja2/environment.py:1256: error: Unused "type: ignore" comment
+ src/jinja2/environment.py:1352: error: Unused "type: ignore" comment
+ src/jinja2/environment.py:1535: error: Unused "type: ignore" comment
+ src/jinja2/environment.py:1567: error: Unused "type: ignore" comment

bokeh (https://github.com/bokeh/bokeh)
+ bokeh/protocol/receiver.py: note: In member "consume" of class "Receiver":
+ bokeh/protocol/receiver.py:137:9: error: Too few arguments  [call-arg]
+ bokeh/protocol/receiver.py:137:9: note: "_current_consumer" is considered instance variable, to make it class variable use ClassVar[...]
+ bokeh/protocol/receiver.py:137:32: error: Argument 1 has incompatible type "Union[str, bytes]"; expected "Receiver"  [arg-type]

discord.py (https://github.com/Rapptz/discord.py)
- discord/gateway.py:380: error: Cannot assign to a method
- discord/member.py:429: error: Attribute function "create_dm" with type "Callable[[], Awaitable[DMChannel]]" does not accept self argument
- discord/client.py:315: error: Cannot assign to a method
- discord/client.py:316: error: Cannot assign to a method
+ discord/ext/commands/core.py:1958: error: Argument 1 has incompatible type "Context[BotT]"; expected "ContextT"
- discord/ext/commands/core.py:1948: error: Invalid self argument "Check[ContextT]" to attribute function "predicate" with type "Callable[[ContextT_co], Coroutine[Any, Any, bool]]"
- discord/ext/commands/core.py:1958: error: Too many arguments
- discord/ext/commands/core.py:1965: error: Argument 1 to "CheckAnyFailure" has incompatible type "List[Callable[[], Coroutine[Any, Any, bool]]]"; expected "List[Callable[[Context[<nothing>]], bool]]"
+ discord/ext/commands/core.py:1965: error: Argument 1 to "CheckAnyFailure" has incompatible type "List[Callable[[ContextT], Coroutine[Any, Any, bool]]]"; expected "List[Callable[[Context[Any]], bool]]"

@ilevkivskyi
Copy link
Member Author

mypy_primer still looks very good. I checked few new errors, they all look expected (and got useful notes pointing at solution).

@ilevkivskyi
Copy link
Member Author

Since this re-applies previously merged PR, I am going to merge this soon unless there are objections.

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

Successfully merging this pull request may close these issues.

Class with function fields incorrectly thinks first argument is self Cannot assign to field of Callable type
3 participants