[ty] infer function's return type
Summary
This PR closes astral-sh/ty#128.
FunctionType::infer_return_type is added to infer the return type of a function when its return type is not specified.
TODOs
- [x] infer simple function's return type ~~- [ ] infer generator's return type~~ ~~- [ ] infer coroutine's return type~~ ~~- [ ] infer lambda function's return type~~
Test Plan
New test cases are added to mdtest/function/return_type.md.
mypy_primer results
Changes were detected when running on open source projects
zipp (https://github.com/jaraco/zipp)
+ zipp/__init__.py:373:29: error[invalid-argument-type] Argument to function `__new__` is incorrect: Expected `str | PathLike[str]`, found `Unknown | str | None`
+ zipp/__init__.py:433:16: error[no-matching-overload] No overload of function `join` matches arguments
+ zipp/glob.py:67:16: error[no-matching-overload] No overload of bound method `join` matches arguments
- Found 4 diagnostics
+ Found 7 diagnostics
attrs (https://github.com/python-attrs/attrs)
+ src/attr/_make.py:453:19: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Self@from_counting_attr | Unknown`
+ src/attr/_make.py:457:19: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Self@from_counting_attr | Unknown`
- src/attr/_make.py:475:35: warning[possibly-missing-attribute] Attribute `init` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:475:35: warning[possibly-missing-attribute] Attribute `init` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:475:59: warning[possibly-missing-attribute] Attribute `kw_only` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:475:59: warning[possibly-missing-attribute] Attribute `kw_only` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:480:37: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:480:37: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:487:16: warning[possibly-missing-attribute] Attribute `alias` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:487:16: warning[possibly-missing-attribute] Attribute `alias` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:489:70: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:489:70: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:493:19: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:493:19: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Unknown | Self@evolve`
- src/attr/_make.py:797:13: error[invalid-assignment] Object of type `ReferenceType[Unknown]` is not assignable to attribute `__attrs_base_of_slotted__` on type `Unknown | type`
+ src/attr/_make.py:797:13: error[invalid-assignment] Object of type `ReferenceType[Unknown | type]` is not assignable to attribute `__attrs_base_of_slotted__` on type `Unknown | type`
+ src/attr/_make.py:809:13: warning[possibly-missing-attribute] Attribute `__attrs_init_subclass__` may be missing on object of type `Unknown | type`
- src/attr/_make.py:1061:13: error[invalid-argument-type] Argument to function `_make_hash_script` is incorrect: Expected `list[Attribute | Unknown]`, found `Unknown | type`
+ src/attr/_make.py:1061:13: error[invalid-argument-type] Argument to function `_make_hash_script` is incorrect: Expected `list[Attribute]`, found `Unknown | type`
- src/attr/_make.py:1608:13: error[invalid-assignment] Object of type `tuple[Attribute | Unknown, ...]` is not assignable to `list[Attribute | Unknown]`
+ src/attr/_make.py:1608:13: error[invalid-assignment] Object of type `tuple[Attribute, ...]` is not assignable to `list[Attribute]`
- src/attr/_make.py:1609:29: warning[possibly-missing-attribute] Attribute `hash` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1609:48: warning[possibly-missing-attribute] Attribute `hash` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1609:67: warning[possibly-missing-attribute] Attribute `eq` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1647:16: warning[possibly-missing-attribute] Attribute `eq_key` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1648:32: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1649:35: warning[possibly-missing-attribute] Attribute `eq_key` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1651:57: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:1654:62: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2189:12: warning[possibly-missing-attribute] Attribute `validator` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2192:21: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2193:26: warning[possibly-missing-attribute] Attribute `on_setattr` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2194:13: warning[possibly-missing-attribute] Attribute `on_setattr` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2198:20: warning[possibly-missing-attribute] Attribute `alias` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2200:34: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2201:48: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2203:12: warning[possibly-missing-attribute] Attribute `converter` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2203:55: warning[possibly-missing-attribute] Attribute `converter` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2204:35: warning[possibly-missing-attribute] Attribute `converter` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2206:25: warning[possibly-missing-attribute] Attribute `converter` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2208:12: warning[possibly-missing-attribute] Attribute `init` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2210:58: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2220:66: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2231:56: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2241:62: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2252:14: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2254:16: warning[possibly-missing-attribute] Attribute `kw_only` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2266:62: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2274:16: warning[possibly-missing-attribute] Attribute `kw_only` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2281:54: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2299:62: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2315:52: warning[possibly-missing-attribute] Attribute `default` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2317:16: warning[possibly-missing-attribute] Attribute `kw_only` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2329:62: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2335:12: warning[possibly-missing-attribute] Attribute `init` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2336:16: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2337:41: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2373:33: warning[possibly-missing-attribute] Attribute `name` may be missing on object of type `Attribute | Unknown`
- src/attr/_make.py:2373:60: warning[possibly-missing-attribute] Attribute `init` may be missing on object of type `Attribute | Unknown`
+ src/attr/_make.py:1609:29: error[unresolved-attribute] Object of type `Attribute` has no attribute `hash`
+ src/attr/_make.py:1609:48: error[unresolved-attribute] Object of type `Attribute` has no attribute `hash`
+ src/attr/_make.py:1609:67: error[unresolved-attribute] Object of type `Attribute` has no attribute `eq`
+ src/attr/_make.py:1647:16: error[unresolved-attribute] Object of type `Attribute` has no attribute `eq_key`
+ src/attr/_make.py:1648:32: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:1649:35: error[unresolved-attribute] Object of type `Attribute` has no attribute `eq_key`
+ src/attr/_make.py:1651:57: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:1654:62: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2189:12: error[unresolved-attribute] Object of type `Attribute` has no attribute `validator`
+ src/attr/_make.py:2192:21: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2193:26: error[unresolved-attribute] Object of type `Attribute` has no attribute `on_setattr`
+ src/attr/_make.py:2194:13: error[unresolved-attribute] Object of type `Attribute` has no attribute `on_setattr`
+ src/attr/_make.py:2198:20: error[unresolved-attribute] Object of type `Attribute` has no attribute `alias`
+ src/attr/_make.py:2200:34: error[unresolved-attribute] Object of type `Attribute` has no attribute `default`
+ src/attr/_make.py:2201:48: error[unresolved-attribute] Object of type `Attribute` has no attribute `default`
+ src/attr/_make.py:2203:12: error[unresolved-attribute] Object of type `Attribute` has no attribute `converter`
+ src/attr/_make.py:2203:55: error[unresolved-attribute] Object of type `Attribute` has no attribute `converter`
+ src/attr/_make.py:2204:35: error[unresolved-attribute] Object of type `Attribute` has no attribute `converter`
+ src/attr/_make.py:2206:25: error[unresolved-attribute] Object of type `Attribute` has no attribute `converter`
+ src/attr/_make.py:2208:12: error[unresolved-attribute] Object of type `Attribute` has no attribute `init`
+ src/attr/_make.py:2210:58: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2220:66: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2231:56: error[unresolved-attribute] Object of type `Attribute` has no attribute `default`
+ src/attr/_make.py:2241:62: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2252:14: error[unresolved-attribute] Object of type `Attribute` has no attribute `default`
+ src/attr/_make.py:2254:16: error[unresolved-attribute] Object of type `Attribute` has no attribute `kw_only`
+ src/attr/_make.py:2266:62: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2274:16: error[unresolved-attribute] Object of type `Attribute` has no attribute `kw_only`
+ src/attr/_make.py:2281:54: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2299:62: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2315:52: error[unresolved-attribute] Object of type `Attribute` has no attribute `default`
+ src/attr/_make.py:2317:16: error[unresolved-attribute] Object of type `Attribute` has no attribute `kw_only`
+ src/attr/_make.py:2329:62: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2335:12: error[unresolved-attribute] Object of type `Attribute` has no attribute `init`
+ src/attr/_make.py:2336:16: error[unresolved-attribute] Object of type `Attribute` has no attribute `type`
+ src/attr/_make.py:2337:41: error[unresolved-attribute] Object of type `Attribute` has no attribute `type`
+ src/attr/_make.py:2373:33: error[unresolved-attribute] Object of type `Attribute` has no attribute `name`
+ src/attr/_make.py:2373:60: error[unresolved-attribute] Object of type `Attribute` has no attribute `init`
+ src/attr/_make.py:2641:13: error[invalid-assignment] Object of type `type` is not assignable to `<class 'Attribute'>`
+ src/attr/_make.py:3038:11: error[invalid-assignment] Object of type `type` is not assignable to `<class 'Factory'>`
+ src/attr/_make.py:3157:13: error[invalid-assignment] Object of type `type` is not assignable to `<class 'Converter'>`
+ src/attr/_make.py:3278:18: error[not-iterable] Object of type `Unknown | _CountingAttr` may not be iterable
+ src/attr/_version_info.py:86:16: error[unsupported-operator] Operator `<` is not supported between objects of type `list[Unknown] | @Todo | tuple[Unknown, ...]` and `Unknown | tuple[Unknown, ...]`
+ src/attr/validators.py:98:34: error[invalid-argument-type] Argument to function `isinstance` is incorrect: Expected `type | tuple[Divergent, ...]`, found `Unknown | _CountingAttr`
+ src/attr/validators.py:137:16: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:138:53: warning[possibly-missing-attribute] Attribute `pattern` may be missing on object of type `Unknown | _CountingAttr`
+ src/attr/validators.py:206:9: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:240:26: error[unsupported-operator] Operator `in` is not supported between objects of type `Unknown` and `Unknown | _CountingAttr`
+ src/attr/validators.py:342:13: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:345:13: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:396:13: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:400:17: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:402:17: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:468:16: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:544:12: error[unsupported-operator] Operator `>` is not supported between objects of type `int` and `Unknown | _CountingAttr`
+ src/attr/validators.py:573:12: error[unsupported-operator] Operator `<` is not supported between objects of type `int` and `Unknown | _CountingAttr`
+ src/attr/validators.py:602:34: error[invalid-argument-type] Argument to function `issubclass` is incorrect: Expected `type | tuple[Divergent, ...]`, found `Unknown | _CountingAttr`
+ src/attr/validators.py:650:13: error[call-non-callable] Object of type `_CountingAttr` is not callable
+ src/attr/validators.py:651:16: error[invalid-exception-caught] Invalid object caught in an exception handler: Object has type `Unknown | _CountingAttr`
+ src/attr/validators.py:655:17: warning[possibly-missing-attribute] Attribute `format` may be missing on object of type `Unknown | _CountingAttr`
+ src/attr/validators.py:710:18: error[not-iterable] Object of type `Unknown | _CountingAttr` may not be iterable
+ tests/test_make.py:1365:16: warning[possibly-missing-attribute] Attribute `__attrs_attrs__` may be missing on object of type `Unknown | type`
+ tests/test_make.py:1380:16: warning[possibly-missing-attribute] Attribute `__attrs_attrs__` may be missing on object of type `Unknown | type`
+ tests/test_make.py:1468:30: warning[possibly-missing-attribute] Attribute `echo` may be missing on object of type `Unknown | type`
+ tests/test_make.py:1487:25: warning[possibly-missing-attribute] Attribute `__attrs_attrs__` may be missing on object of type `Unknown | type`
+ tests/test_make.py:3051:30: warning[possibly-missing-attribute] Attribute `__match_args__` may be missing on object of type `Unknown | type`
+ tests/test_make.py:3057:22: warning[possibly-missing-attribute] Attribute `__match_args__` may be missing on object of type `Unknown | type`
+ tests/test_make.py:3060:26: warning[possibly-missing-attribute] Attribute `__match_args__` may be missing on object of type `Unknown | type`
- Found 616 diagnostics
+ Found 649 diagnostics
parso (https://github.com/davidhalter/parso)
+ parso/__init__.py:58:26: error[invalid-argument-type] Argument to bound method `parse` is incorrect: Expected `str | bytes`, found `Unknown | None`
- parso/grammar.py:163:27: warning[unused-ignore-comment] Unused blanket `type: ignore` directive
+ parso/grammar.py:199:16: warning[possibly-missing-attribute] Attribute `walk` may be missing on object of type `Unknown | None | Normalizer`
+ parso/grammar.py:203:9: warning[possibly-missing-attribute] Attribute `walk` may be missing on object of type `Unknown | None | Normalizer`
+ parso/grammar.py:204:16: warning[possibly-missing-attribute] Attribute `issues` may be missing on object of type `Unknown | None | Normalizer`
+ parso/pgen2/grammar_parser.py:106:20: error[not-iterable] Object of type `None` is not iterable
+ parso/python/diff.py:423:17: error[not-subscriptable] Cannot subscript object of type `None` with no `__getitem__` method
+ parso/python/diff.py:621:16: warning[possibly-missing-attribute] Attribute `tree_node` may be missing on object of type `Unknown | None`
+ parso/python/diff.py:622:9: warning[possibly-missing-attribute] Attribute `add_tree_nodes` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:783:12: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:784:26: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:784:54: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:1166:20: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:1167:34: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | None`
+ parso/python/errors.py:1167:62: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | None`
- parso/python/pep8.py:362:17: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | IndentationNode | None`
+ parso/python/pep8.py:362:17: warning[possibly-missing-attribute] Attribute `type` may be missing on object of type `Unknown | None | IndentationNode`
- parso/python/pep8.py:363:37: warning[possibly-missing-attribute] Attribute `parent` may be missing on object of type `Unknown | IndentationNode | None`
+ parso/python/pep8.py:363:37: warning[possibly-missing-attribute] Attribute `parent` may be missing on object of type `Unknown | None | IndentationNode`
- parso/python/tokenize.py:109:9: error[invalid-assignment] Invalid subscript assignment with key of type `tuple[Unknown, ...]` and value of type `Unknown` on object of type `dict[PythonVersionInfo, TokenCollection]`
+ parso/python/tokenize.py:109:9: error[invalid-assignment] Invalid subscript assignment with key of type `tuple[Unknown, ...]` and value of type `TokenCollection` on object of type `dict[PythonVersionInfo, TokenCollection]`
+ parso/python/tokenize.py:588:31: error[invalid-assignment] Object of type `Pattern[Unknown] | None` is not assignable to `Pattern[Unknown]`
+ parso/python/tree.py:135:21: warning[possibly-missing-attribute] Attribute `token_type` may be missing on object of type `(Unknown & ~None) | NodeOrLeaf`
+ parso/python/tree.py:1129:20: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | NodeOrLeaf`
+ parso/python/tree.py:1130:24: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | NodeOrLeaf`
+ parso/python/tree.py:1131:26: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | NodeOrLeaf`
+ parso/python/tree.py:1149:20: warning[possibly-missing-attribute] Attribute `children` may be missing on object of type `Unknown | NodeOrLeaf`
+ parso/tree.py:447:16: warning[possibly-missing-attribute] Attribute `replace` may be missing on object of type `Unknown | None`
- Found 199 diagnostics
+ Found 219 diagnostics
kornia (https://github.com/kornia/kornia)
+ kornia/feature/dedode/transformer/dinov2.py:317:30: error[invalid-argument-type] Method `__getitem__` of type `Overload[(i: SupportsIndex, /) -> Unknown, (s: slice[Any, Any, Any], /) -> list[Unknown]]` cannot be called with key of type `Literal["x_norm_clstoken"]` on object of type `list[Unknown]`
- Found 758 diagnostics
+ Found 759 diagnostics
pip (https://github.com/pypa/pip)
+ src/pip/_internal/cli/cmdoptions.py:123:51: error[invalid-argument-type] Argument to function `get_file_content` is incorrect: Expected `PipSession`, found `Self@__enter__ | Unknown`
+ src/pip/_internal/commands/index.py:119:17: error[invalid-argument-type] Argument to bound method `_build_package_finder` is incorrect: Expected `PipSession`, found `Self@__enter__ | Unknown`
+ src/pip/_internal/commands/list.py:245:58: error[invalid-argument-type] Argument to bound method `_build_package_finder` is incorrect: Expected `PipSession`, found `Self@__enter__ | Unknown`
+ src/pip/_internal/index/collector.py:311:9: error[invalid-argument-type] Argument is incorrect: Expected `bytes`, found `(Unknown & ~Literal[False]) | None | (bytes & ~AlwaysFalsy) | Literal[b""]`
- src/pip/_vendor/cachecontrol/adapter.py:162:39: warning[unused-ignore-comment] Unused blanket `type: ignore` directive
- src/pip/_vendor/cachecontrol/serialize.py:35:46: warning[unused-ignore-comment] Unused blanket `type: ignore` directive
+ src/pip/_vendor/cachecontrol/serialize.py:36:45: error[invalid-argument-type] Argument to function `len` is incorrect: Expected `Sized`, found `None | bytes | Unknown`
+ src/pip/_vendor/cachecontrol/serialize.py:146:47: error[invalid-argument-type] Argument to bound method `prepare_response` is incorrect: Expected `Mapping[str, Any]`, found `int | Unknown | None | ... omitted 9 union elements`
+ src/pip/_vendor/distlib/compat.py:1127:22: error[call-non-callable] Object of type `ModuleType` is not callable
+ src/pip/_vendor/distlib/resources.py:196:33: error[not-iterable] Object of type `Unknown | Self@__get__` may not be iterable
+ src/pip/_vendor/distlib/resources.py:196:33: warning[possibly-missing-attribute] Attribute `resources` may be missing on object of type `Unknown | ResourceContainer | Resource`
+ src/pip/_vendor/distlib/resources.py:202:28: warning[possibly-missing-attribute] Attribute `is_container` may be missing on object of type `None | ResourceContainer | Resource | Unknown`
+ src/pip/_vendor/msgpack/fallback.py:540:29: error[invalid-argument-type] Argument to function `__new__` is incorrect: Expected `Iterable[SupportsIndex] | SupportsIndex | SupportsBytes | Buffer`, found `None | Unknown | int | bytearray`
+ src/pip/_vendor/msgpack/fallback.py:542:23: warning[possibly-missing-attribute] Attribute `decode` may be missing on object of type `None | Unknown | int | bytearray`
+ src/pip/_vendor/msgpack/fallback.py:545:26: error[invalid-argument-type] Argument to function `__new__` is incorrect: Expected `Iterable[SupportsIndex] | SupportsIndex | SupportsBytes | Buffer`, found `None | Unknown | int | bytearray`
+ src/pip/_vendor/msgpack/fallback.py:548:49: error[invalid-argument-type] Argument to function `__new__` is incorrect: Expected `Iterable[SupportsIndex] | SupportsIndex | SupportsBytes | Buffer`, found `None | Unknown | int | bytearray`
+ src/pip/_vendor/msgpack/fallback.py:558:48: error[invalid-argument-type] Argument to function `__new__` is incorrect: Expected `Iterable[SupportsIndex] | SupportsIndex | SupportsBytes | Buffer`, found `None | Unknown | int | bytearray`
+ src/pip/_vendor/pkg_resources/__init__.py:2308:28: error[invalid-argument-type] Argument to function `distributions_from_metadata` is incorrect: Expected `str`, found `str | bytes`
+ src/pip/_vendor/pkg_resources/__init__.py:2308:28: error[invalid-argument-type] Argument to function `find_distributions` is incorrect: Expected `str`, found `str | bytes`
+ src/pip/_vendor/pkg_resources/__init__.py:2828:13: error[invalid-assignment] Invalid subscript assignment with key of type `Unknown | str` and value of type `Self@parse | Unknown` on object of type `dict[str, Self@parse_group]`
+ src/pip/_vendor/pkg_resources/__init__.py:2852:13: error[invalid-assignment] Invalid subscript assignment with key of type `str` and value of type `dict[str, Self@parse_group] | Unknown` on object of type `dict[str, dict[str, Self@parse_map]]`
+ src/pip/_vendor/pkg_resources/__init__.py:2941:16: error[unsupported-operator] Operator `<` is not supported between two objects of type `tuple[Unknown | Version, Unknown | int, Unknown | str, Unknown | str | None, (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""], (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""]]`
+ src/pip/_vendor/pkg_resources/__init__.py:2944:16: error[unsupported-operator] Operator `<=` is not supported between two objects of type `tuple[Unknown | Version, Unknown | int, Unknown | str, Unknown | str | None, (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""], (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""]]`
+ src/pip/_vendor/pkg_resources/__init__.py:2947:16: error[unsupported-operator] Operator `>` is not supported between two objects of type `tuple[Unknown | Version, Unknown | int, Unknown | str, Unknown | str | None, (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""], (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""]]`
+ src/pip/_vendor/pkg_resources/__init__.py:2950:16: error[unsupported-operator] Operator `>=` is not supported between two objects of type `tuple[Unknown | Version, Unknown | int, Unknown | str, Unknown | str | None, (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""], (Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[""]]`
- src/pip/_vendor/pkg_resources/__init__.py:3466:40: error[invalid-argument-type] Argument to bound method `contains` is incorrect: Expected `Version | str`, found `(str & ~Distribution) | (tuple[str, ...] & ~Distribution) | Unknown`
+ src/pip/_vendor/pkg_resources/__init__.py:3466:40: error[invalid-argument-type] Argument to bound method `contains` is incorrect: Expected `Version | str`, found `str | (tuple[str, ...] & ~Distribution) | Unknown`
+ src/pip/_vendor/pygments/lexers/python.py:362:42: error[invalid-argument-type] Argument to function `fstring_rules` is incorrect: Expected `PythonLexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/lexers/python.py:363:42: error[invalid-argument-type] Argument to function `fstring_rules` is incorrect: Expected `PythonLexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/lexers/python.py:364:45: error[invalid-argument-type] Argument to function `innerstring_rules` is incorrect: Expected `PythonLexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/lexers/python.py:365:45: error[invalid-argument-type] Argument to function `innerstring_rules` is incorrect: Expected `PythonLexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/lexers/python.py:611:45: error[invalid-argument-type] Argument to function `innerstring_rules` is incorrect: Expected `Python2Lexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/lexers/python.py:612:45: error[invalid-argument-type] Argument to function `innerstring_rules` is incorrect: Expected `Python2Lexer`, found `Any | _TokenType`
+ src/pip/_vendor/pygments/sphinxext.py:108:26: warning[possibly-missing-attribute] Attribute `filenames` may be missing on object of type `Unknown | None`
+ src/pip/_vendor/pygments/sphinxext.py:108:48: warning[possibly-missing-attribute] Attribute `alias_filenames` may be missing on object of type `Unknown | None`
+ src/pip/_vendor/pygments/sphinxext.py:111:46: warning[possibly-missing-attribute] Attribute `url` may be missing on object of type `Unknown | None`
+ src/pip/_vendor/requests/models.py:121:26: error[not-iterable] Object of type `None | list[Unknown]` may not be iterable
+ src/pip/_vendor/requests/models.py:155:27: error[not-iterable] Object of type `None | list[Unknown]` may not be iterable
+ src/pip/_vendor/requests/models.py:173:21: error[not-iterable] Object of type `None | list[Unknown]` may not be iterable
+ src/pip/_vendor/requests/models.py:602:17: error[call-non-callable] Object of type `tuple[str, str]` is not callable
- src/pip/_vendor/requests/models.py:935:41: error[invalid-argument-type] Argument to class `str` is incorrect: Expected `str`, found `Unknown | None`
+ src/pip/_vendor/requests/models.py:935:41: error[invalid-argument-type] Argument to class `str` is incorrect: Expected `str`, found `Unknown | None | Literal["utf-8"]`
+ src/pip/_vendor/requests/sessions.py:80:5: error[no-matching-overload] No overload of bound method `update` matches arguments
+ src/pip/_vendor/requests/utils.py:615:31: error[invalid-argument-type] Argument to class `str` is incorrect: Expected `str`, found `None | Unknown | Literal["ISO-8859-1", "utf-8"]`
+ src/pip/_vendor/rich/syntax.py:167:27: error[unsupported-operator] Operator `+` is not supported between objects of type `Literal["#"]` and `(Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[True]`
+ src/pip/_vendor/rich/syntax.py:168:29: error[unsupported-operator] Operator `+` is not supported between objects of type `Literal["#"]` and `(Unknown & ~AlwaysFalsy) | (str & ~AlwaysFalsy) | Literal[True]`
+ src/pip/_vendor/rich/syntax.py:169:21: error[invalid-argument-type] Argument to bound method `__init__` is incorrect: Expected `bool | None`, found `Unknown | str | None | bool`
+ src/pip/_vendor/rich/syntax.py:170:21: error[invalid-argument-type] Argument to bound method `__init__` is incorrect: Expected `bool | None`, found `Unknown | str | None | bool`
+ src/pip/_vendor/rich/syntax.py:171:21: error[invalid-argument-type] Argument to bound method `__init__` is incorrect: Expected `bool | None`, found `Unknown | str | None | bool`
- src/pip/_vendor/urllib3/connectionpool.py:785:21: warning[possibly-missing-attribute] Attribute `proxy` may be missing on object of type `None | Unknown`
+ src/pip/_vendor/urllib3/connectionpool.py:785:21: warning[possibly-missing-attribute] Attribute `proxy` may be missing on object of type `None | Unknown | HTTPConnection`
- src/pip/_vendor/urllib3/connectionpool.py:786:21: warning[possibly-missing-attribute] Attribute `proxy` may be missing on object of type `None | Unknown`
+ src/pip/_vendor/urllib3/connectionpool.py:786:21: warning[possibly-missing-attribute] Attribute `proxy` may be missing on object of type `None | Unknown | HTTPConnection`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:136:5: warning[possibly-missing-attribute] Attribute `SecItemImport` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:146:5: warning[possibly-missing-attribute] Attribute `SecItemImport` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:148:5: warning[possibly-missing-attribute] Attribute `SecCertificateGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:149:5: warning[possibly-missing-attribute] Attribute `SecCertificateGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:151:5: warning[possibly-missing-attribute] Attribute `SecIdentityGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:152:5: warning[possibly-missing-attribute] Attribute `SecIdentityGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:154:5: warning[possibly-missing-attribute] Attribute `SecKeyGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:155:5: warning[possibly-missing-attribute] Attribute `SecKeyGetTypeID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:157:5: warning[possibly-missing-attribute] Attribute `SecCertificateCreateWithData` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:158:5: warning[possibly-missing-attribute] Attribute `SecCertificateCreateWithData` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:160:5: warning[possibly-missing-attribute] Attribute `SecCertificateCopyData` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:161:5: warning[possibly-missing-attribute] Attribute `SecCertificateCopyData` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:163:5: warning[possibly-missing-attribute] Attribute `SecCopyErrorMessageString` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:164:5: warning[possibly-missing-attribute] Attribute `SecCopyErrorMessageString` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:166:5: warning[possibly-missing-attribute] Attribute `SecIdentityCreateWithCertificate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:171:5: warning[possibly-missing-attribute] Attribute `SecIdentityCreateWithCertificate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:173:5: warning[possibly-missing-attribute] Attribute `SecKeychainCreate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:181:5: warning[possibly-missing-attribute] Attribute `SecKeychainCreate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:183:5: warning[possibly-missing-attribute] Attribute `SecKeychainDelete` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:184:5: warning[possibly-missing-attribute] Attribute `SecKeychainDelete` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:186:5: warning[possibly-missing-attribute] Attribute `SecPKCS12Import` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:191:5: warning[possibly-missing-attribute] Attribute `SecPKCS12Import` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:198:5: warning[possibly-missing-attribute] Attribute `SSLSetIOFuncs` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:199:5: warning[possibly-missing-attribute] Attribute `SSLSetIOFuncs` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:201:5: warning[possibly-missing-attribute] Attribute `SSLSetPeerID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:202:5: warning[possibly-missing-attribute] Attribute `SSLSetPeerID` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:204:5: warning[possibly-missing-attribute] Attribute `SSLSetCertificate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:205:5: warning[possibly-missing-attribute] Attribute `SSLSetCertificate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:207:5: warning[possibly-missing-attribute] Attribute `SSLSetCertificateAuthorities` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:208:5: warning[possibly-missing-attribute] Attribute `SSLSetCertificateAuthorities` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:210:5: warning[possibly-missing-attribute] Attribute `SSLSetConnection` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:211:5: warning[possibly-missing-attribute] Attribute `SSLSetConnection` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:213:5: warning[possibly-missing-attribute] Attribute `SSLSetPeerDomainName` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:214:5: warning[possibly-missing-attribute] Attribute `SSLSetPeerDomainName` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:216:5: warning[possibly-missing-attribute] Attribute `SSLHandshake` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:217:5: warning[possibly-missing-attribute] Attribute `SSLHandshake` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:219:5: warning[possibly-missing-attribute] Attribute `SSLRead` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:220:5: warning[possibly-missing-attribute] Attribute `SSLRead` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:222:5: warning[possibly-missing-attribute] Attribute `SSLWrite` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:223:5: warning[possibly-missing-attribute] Attribute `SSLWrite` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:225:5: warning[possibly-missing-attribute] Attribute `SSLClose` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:226:5: warning[possibly-missing-attribute] Attribute `SSLClose` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:228:5: warning[possibly-missing-attribute] Attribute `SSLGetNumberSupportedCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:229:5: warning[possibly-missing-attribute] Attribute `SSLGetNumberSupportedCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:231:5: warning[possibly-missing-attribute] Attribute `SSLGetSupportedCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:236:5: warning[possibly-missing-attribute] Attribute `SSLGetSupportedCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:238:5: warning[possibly-missing-attribute] Attribute `SSLSetEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:243:5: warning[possibly-missing-attribute] Attribute `SSLSetEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:245:5: error[unresolved-attribute] Unresolved attribute `argtype` on type `_NamedFuncPointer`.
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:245:5: warning[possibly-missing-attribute] Attribute `SSLGetNumberEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:246:5: warning[possibly-missing-attribute] Attribute `SSLGetNumberEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:248:5: warning[possibly-missing-attribute] Attribute `SSLGetEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:253:5: warning[possibly-missing-attribute] Attribute `SSLGetEnabledCiphers` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:255:5: warning[possibly-missing-attribute] Attribute `SSLGetNegotiatedCipher` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:256:5: warning[possibly-missing-attribute] Attribute `SSLGetNegotiatedCipher` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:258:5: warning[possibly-missing-attribute] Attribute `SSLGetNegotiatedProtocolVersion` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:262:5: warning[possibly-missing-attribute] Attribute `SSLGetNegotiatedProtocolVersion` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:264:5: warning[possibly-missing-attribute] Attribute `SSLCopyPeerTrust` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:265:5: warning[possibly-missing-attribute] Attribute `SSLCopyPeerTrust` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:267:5: warning[possibly-missing-attribute] Attribute `SecTrustSetAnchorCertificates` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:268:5: warning[possibly-missing-attribute] Attribute `SecTrustSetAnchorCertificates` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:270:5: error[unresolved-attribute] Unresolved attribute `argstypes` on type `_NamedFuncPointer`.
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:270:5: warning[possibly-missing-attribute] Attribute `SecTrustSetAnchorCertificatesOnly` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:271:5: warning[possibly-missing-attribute] Attribute `SecTrustSetAnchorCertificatesOnly` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:273:5: warning[possibly-missing-attribute] Attribute `SecTrustEvaluate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:274:5: warning[possibly-missing-attribute] Attribute `SecTrustEvaluate` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:276:5: warning[possibly-missing-attribute] Attribute `SecTrustGetCertificateCount` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:277:5: warning[possibly-missing-attribute] Attribute `SecTrustGetCertificateCount` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:279:5: warning[possibly-missing-attribute] Attribute `SecTrustGetCertificateAtIndex` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:280:5: warning[possibly-missing-attribute] Attribute `SecTrustGetCertificateAtIndex` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:282:5: warning[possibly-missing-attribute] Attribute `SSLCreateContext` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:287:5: warning[possibly-missing-attribute] Attribute `SSLCreateContext` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:289:5: warning[possibly-missing-attribute] Attribute `SSLSetSessionOption` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:290:5: warning[possibly-missing-attribute] Attribute `SSLSetSessionOption` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:292:5: warning[possibly-missing-attribute] Attribute `SSLSetProtocolVersionMin` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:293:5: warning[possibly-missing-attribute] Attribute `SSLSetProtocolVersionMin` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:295:5: warning[possibly-missing-attribute] Attribute `SSLSetProtocolVersionMax` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:296:5: warning[possibly-missing-attribute] Attribute `SSLSetProtocolVersionMax` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:299:9: warning[possibly-missing-attribute] Attribute `SSLSetALPNProtocols` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:300:9: warning[possibly-missing-attribute] Attribute `SSLSetALPNProtocols` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:305:5: warning[possibly-missing-attribute] Attribute `SecCopyErrorMessageString` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:306:5: warning[possibly-missing-attribute] Attribute `SecCopyErrorMessageString` may be missing on object of type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:308:5: error[invalid-assignment] Object of type `type[_CFunctionType]` is not assignable to attribute `SSLReadFunc` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:309:5: error[invalid-assignment] Object of type `type[_CFunctionType]` is not assignable to attribute `SSLWriteFunc` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:310:5: error[invalid-assignment] Object of type `type[_Pointer[c_void_p]]` is not assignable to attribute `SSLContextRef` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:311:5: error[invalid-assignment] Object of type `<class 'c_uint32'>` is not assignable to attribute `SSLProtocol` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:312:5: error[invalid-assignment] Object of type `<class 'c_uint32'>` is not assignable to attribute `SSLCipherSuite` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:313:5: error[invalid-assignment] Object of type `type[_Pointer[c_void_p]]` is not assignable to attribute `SecIdentityRef` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:314:5: error[invalid-assignment] Object of type `type[_Pointer[c_void_p]]` is not assignable to attribute `SecKeychainRef` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:315:5: error[invalid-assignment] Object of type `type[_Pointer[c_void_p]]` is not assignable to attribute `SecTrustRef` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:316:5: error[invalid-assignment] Object of type `<class 'c_uint32'>` is not assignable to attribute `SecTrustResultType` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:317:5: error[invalid-assignment] Object of type `<class 'c_uint32'>` is not assignable to attribute `SecExternalFormat` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:318:5: error[invalid-assignment] Object of type `<class 'c_int32'>` is not assignable to attribute `OSStatus` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:320:5: error[invalid-assignment] Object of type `_Pointer[c_void_p]` is not assignable to attribute `kSecImportExportPassphrase` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:321:9: error[invalid-argument-type] Argument to bound method `in_dll` is incorrect: Expected `CDLL`, found `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:323:5: error[invalid-assignment] Object of type `_Pointer[c_void_p]` is not assignable to attribute `kSecImportItemIdentity` on type `CDLL | None`
+ src/pip/_vendor/urllib3/contrib/_securetransport/bindings.py:324:9: error[invalid-argument-type] Argument to bound method `in_dll` is
... (truncated 65012 lines) ...
Memory usage changes were detected when running on open source projects
trio (https://github.com/python-trio/trio)
- struct metadata = ~10MB
+ struct metadata = ~11MB
- struct fields = ~11MB
+ struct fields = ~12MB
- memo fields = ~108MB
+ memo fields = ~113MB
prefect (https://github.com/PrefectHQ/prefect)
- memo metadata = ~167MB
+ memo metadata = ~176MB
Most of the changes detected by mypy_primer appear to be due to ill-typed code errors now being caught correctly.
Code like the following now produces false positive warnings, but this may be resolved by type narrowing of the instance attributes, which I'm currently working on as a separate issue.
from typing import reveal_type
class C:
def __init__(self):
self.x: int = 1
class D:
def __init__(self):
self.c: C | None = None
def get_d():
return D()
d = get_d()
d.c = C()
# TODO: no error
# error: [possibly-unbound-attribute] "Attribute `x` on type `C | None` is possibly unbound"
reveal_type(d.c.x) # revealed: int
Thank you for looking into this!
but this may be resolved by type narrowing of the instance attributes, which I'm currently working on as a separate issue
I'm assuming you're talking about https://github.com/astral-sh/ty/issues/164? Good to know that you are already working on this, because I planned to do that this week :smile:. I think it would be great to work on this first. Narrowing on attribute expressions will lead to a large reduction in false positives. And it seems like it would help us evaluate the ecosystem changes in this PR more clearly, if we implement narrowing on attribute assignments first.
If a function contains a yield expression, i.e. if it is a generator, current type inference is incorrect. But supporting this requires solving another issues, so I will leave it as a TODO for now.
As for return type inference for normal functions, I think the work is completed.
Sorry that I haven't gotten around to reviewing this PR yet. There's just been a lot to do, and providing this feature is lower on my priority list than some other features. But I realize that places a burden on you to keep it up to date with (rapidly changing) main branch. But I will try to find time to review it soon.
CodSpeed Performance Report
Merging #17371 will degrade performance by 39.89%
Comparing mtshiba:infer-return-type (f5e5165) with main (f619783)
Summary
❌ 4 regressions
✅ 48 untouched
:warning: Please fix the performance issues or acknowledge them on CodSpeed.
Benchmarks breakdown
| Mode | Benchmark | BASE |
HEAD |
Efficiency | |
|---|---|---|---|---|---|
| ❌ | WallTime | sympy |
52.1 s | 86.6 s | -39.89% |
| ❌ | WallTime | pandas |
64.8 s | 68.5 s | -5.51% |
| ❌ | WallTime | freqtrade |
8.1 s | 8.5 s | -5.26% |
| ❌ | Simulation | attrs |
436.2 ms | 498.8 ms | -12.54% |
Since ty has type inference by fixed-point iteration, I thought that this PR would be able to infer the return type for recursive functions without any additional work. But, it seems that this is incorrect in some cases.
def divergent(value):
if type(value) is tuple:
return (divergent(value[0]),)
else:
return None
The return type inference for this function diverges because it becomes tuple[tuple[tuple[...] | None] | None] | None. We need to detect and suppress this kind of divergence.
A formally complete solution to the problem is to synthesize a recursive type, that is, to infer it as follows:
type NestedTuple[T] = T | tuple[NestedTuple[T]]
def divergent[T](value: NestedTuple[T]) -> NestedTuple[None]:
if type(value) is tuple:
return (divergent(value[0]),)
else:
return None
I'm not sure if this is actually possible in Python's type system. ML languages provide complete type inference, including for recursive functions, but it may only be possible due to the nature of the lack of narrowing and subtyping.
So a practical solution would be to detect unstoppable recursion at some point and make the resulting type some kind of gradual type.
This is still troublesome, simply stopping the recursion at some point and falling back to Unknown will still not allow a fixed point to be reached (in the case of a divergent type, the next revision will end up with a type like tuple[Unknown] | None).
Also, functions with many returns will cause the resulting union type to grow explosively within cycles, so if the recursion is not detected within the first few cycles, a significant amount of time/memory will be consumed.
One approach I'm thinking of is to classify recursive functions as divergent / non-divergent (such as fibonacci/even/odd) and monitor them with TypeInferenceBuilder. If the former is detected, replace the divergent part of the union of the function's return type with Unknown in both Type::infer_return_type and TypeInference::infer_return_type. This attempts to discover divergence syntactically.
Another approach is to limit not only the number of elements (= "width") but also the "depth" when building union types. We currently limit the maximum number of literals a union type can have to 200. This is mainly for an optimization, but it also helps to prevent union types from diverging. So what about limiting the depth of a union type as well? (or limit the total number of types in a union type ≃ depth * width)
This PR seems to blow up the runtime for the large wall-time benchmark.
This PR seems to blow up the runtime for the large wall-time benchmark.
I suspect this is caused by an exploding union type when trying to infer the return type of a divergent recursive function.
For example, this function is causing a hang: https://github.com/quora/asynq/blob/1bf4f7b5596401000c8db92a5e08a667d11092b2/asynq/async_task.py#L427-L471
I think the issues we run into here on some recursive functions are closely related to the existing issues we have with recursive type aliases.
ruff-ecosystem results
Linter (stable)
✅ ecosystem check detected no linter changes.
Linter (preview)
✅ ecosystem check detected no linter changes.
CodSpeed WallTime Performance Report
Merging #17371 will degrade performances by 32.81%
Comparing mtshiba:infer-return-type (706eff8) with main (edeb458)
Summary
❌ 2 regressions
✅ 6 untouched
:warning: Please fix the performance issues or acknowledge them on CodSpeed.
Benchmarks breakdown
| Benchmark | BASE |
HEAD |
Change | |
|---|---|---|---|---|
| ❌ | large[sympy] |
44.1 s | 65.6 s | -32.81% |
| ❌ | medium[pandas] |
32.5 s | 34 s | -4.19% |
Diagnostic diff on typing conformance tests
No changes detected when running ty on typing conformance tests ✅
The cycle-detection by manually maintaining a stack of function scopes we are inferring is interesting; I've considered something similar for recursive type aliases, but I've been trying to avoid it. I need to think about that a bit more -- it seems like it can introduce non-determinism, depending on what call we try to infer first?
As you point out, this change definitely introduces non-determinism that affects the inference results, and I strongly feel that we should look for an alternative way. (I confirmed that even without stack overflows, the number of errors in mypy_primer results fluctuates each time during multi-threaded execution. If I understand correctly, salsa assumes that query functions are pure, and having manual call stack breaks this assumption. This must be the cause of the non-determinism.)
Marking this draft for now; please mark ready when its ready for review again. (This just helps streamline my notifications workflow.)
The causes of the false positives reported by mypy_primer are as follows:
incomplete decorator support (sympy)
The arithmetic operations on the Expr class are not working correctly. Decorated function inference is not supported yet.
https://github.com/sympy/sympy/blob/5bb8ffb0dd2d21af10d2fa3c0a3710bba4c11d76/sympy/core/expr.py#L249-L252
submodule resolution issue (scrapy)
The scrapy.signals module is being interpreted as a Tuple[Unknown, Unknown, Unknown] type. This is likely because __getattr__ defined in scrapy/__init__.py returns a three-element tuple. ~~However, it is unclear to me why attribute resolution via __getattr__ takes precedence due to function return type inference.~~
Previously, __getattr__ defined in the module did not specify a return type, so scrapy.signals was interpreted as Unknown, but now it recognizes that __getattr__ returns a tuple, so an error occurs.
This may be related to https://github.com/astral-sh/ty/issues/1053
others
The following errors are consistent with the current Python type spec.
- implicit overloading For example, a function like this:
def f(type):
if type is int:
return 1
elif type is str:
return "a"
reveal_type(f(int)) # revealed: Literal[1, "a"] | None
f(int) + 1 # error
-
__slots__(attrs) Attributes defined with__slots__are reported as unresolved. -
setattr(sympy, etc.) Attributes set withsetattrare reported as unresolved. I think it would be possible in principle to make attributes set with a literal string be recognized as class attributes, but no other type checker does this.
The main remaining concern is performance. According to the codspeed report, sympy's check time has worsened by about 30%. But I believe this is a necessary trade-off.
I believe this is due to an increase in the number of checks, that is, there is a cost to addressing errors/inferences that have been overlooked by Unknown. In fact, the number of errors reported in sympy has increased from about 10,000 to about 70,000 (for reference, pyright reports approximately 35,000 errors).
Here are the local measurements of the sympy check times for each type checker:
ty(main):
$ hyperfine -i "ty check"
Benchmark 1: ty check
Time (mean ± σ): 1.901 s ± 0.118 s [User: 20.211 s, System: 3.641 s]
Range (min … max): 1.799 s … 2.188 s 10 runs
ty(#17371):
$ hyperfine -i "ty check"
Benchmark 1: ty check
Time (mean ± σ): 7.290 s ± 1.341 s [User: 28.048 s, System: 3.558 s]
Range (min … max): 5.232 s … 9.058 s 10 runs
pyright:
$ hyperfine -i "pyright"
Benchmark 1: pyright
Time (mean ± σ): 118.239 s ± 7.783 s [User: 163.368 s, System: 4.845 s]
Range (min … max): 110.686 s … 139.539 s 10 runs
mypy:
$ hyperfine -i "mypy -p sympy --no-incremental"
Benchmark 1: mypy -p sympy --no-incremental
Time (mean ± σ): 35.555 s ± 2.398 s [User: 31.747 s, System: 3.255 s]
Range (min … max): 33.484 s … 39.311 s 10 runs
mypy(check-untyped-defs):
$ hyperfine -i "mypy -p sympy --no-incremental --check-untyped-defs"
Benchmark 1: mypy -p sympy --no-incremental --check-untyped-defs
Time (mean ± σ): 69.795 s ± 0.740 s [User: 66.414 s, System: 2.764 s]
Range (min … max): 68.843 s … 70.830 s 10 runs
pyright is generally considered faster than mypy, but its inferiority in sympy's inspection time suggests that return type inference and its impact are heavy in some cases.
Wait, we might be able to get a better result.
Currently, we converge the return type by replacing "types containing Divergent types" (let's call these recursive types) with Divergent types. However, this is a bit unsatisfactory because it loses some of the structure of the return type.
So instead, we replace the recursive type contained within the "type containing a recursive type" (let's call this a nested recursive type) with Divergent types.
For example, consider the following function:
def f(n):
if n == 0:
return 0
elif n % 2 == 0:
return [f(n-1)]
else:
return (f(n-1),)
The return type of this function is μ X. Literal[0] | list[X] | tuple[X] according to recursive type theory.
The type variable X in this recursive type corresponds to our Divergent.
At the 0th iteration, we obtain Literal[0] | tuple[Divergent] | list[Divergent]. We leave the recursive type as is.
At the 1st iteration, we obtain Literal[0] | tuple[Literal[0] | tuple[Divergent] | list[Divergent]] | list[Literal[0] | tuple[Divergent] | list[Divergent]]. Since this is a nested recursive type, we will "lower" it.
Literal[0] | tuple[Literal[0] | tuple[Divergent] | list[Divergent]] | list[Literal[0] | tuple[Divergent] | list[Divergent]]
=> Literal[0] | tuple[Literal[0] | Divergent | Divergent] | list[Literal[0] | Divergent | Divergent]
=> Literal[0] | tuple[Literal[0] | Divergent] | list[Literal[0] | Divergent]
=> Literal[0] | tuple[Divergent] | list[Divergent]
Since this is the same as the value from the 0th iteration, it is converged. We have obtained a type with the exact same structure as the recursive type!
The final conversion can be achieved with the following rule: G[T | Divergent] = G[Divergent]
This is allowed because T is expected to appear at the top level of the return type, as in T | G[T | Divergent].
To summarize the rules here:
-
T | Divergent = T (T is a non-recursive type) -
G[R] = G[Divergent] (R is a recursive type, e.g. G[Divergent]) -
G[T | Divergent] = G[Divergent] (T is a non-recursive type)
Yes, I think that makes sense, and corresponds to what I did in the final version of https://github.com/astral-sh/ruff/pull/20333 for tuple literals: if any element of the tuple we are constructing contains Divergent (is a recursive type), it is replaced by Divergent. This allowed me to get the result Unknown | tuple[Divergent, Literal[0] in the test in that PR (we can ignore the Unknown, it comes from our general policy of unioning un-annotated attribute types with Unknown) rather than just Unknown | Divergent.
I was planning to next apply this approach to all generic specializations (not just tuple literals) so as to solve Salsa "too many iterations" panics on many more cases of recursive type aliases. I don't want to conflict if you are doing similar work in this PR, but I do think we can and should implement this as a separate PR from return type inference.
T | Divergent = T (T is a non-recursive type)
G[R] = G[Divergent] (R is a recursive type, e.g. G[Divergent])
G[T | Divergent] = G[Divergent] (T is a non-recursive type)
It seems challenging to implement both rule 1 and rule 3, as they seem contradictory (or at least require some kind of context-sensitive handling). Do you have a plan for this?
T | Divergent = T (T is a non-recursive type)G[R] = G[Divergent] (R is a recursive type, e.g. G[Divergent])G[T | Divergent] = G[Divergent] (T is a non-recursive type)It seems challenging to implement both rule 1 and rule 3, as they seem contradictory (or at least require some kind of context-sensitive handling). Do you have a plan for this?
I realized that this could actually be implemented as normalization rules for recursive types rather than rules for union types.
In 69953ff67d57a15500511ac9c53a6a53271e9d21, I added a mode to NormalizedVisitor that normalizes recursive types. NormalizedVisitor retains the nesting level of the type currently visiting, and changes the normalization handling depending on the nesting level (the nesting level increases by one inside a tuple, etc.; the nesting level remains unchanged inside a union).
- If
Divergentappears at level 0, it is replaced withNever. (e.g.Divergent | int => int) - If a recursive type appears at level 1 or above, it is replaced with
Divergent. (e.g.tuple[tuple[Divergent]] => tuple[Divergent], tuple[Divergent | int] => tuple[Divergent])
I see how that could work, as a type transform that we would use in place of the simpler "if ty.has_divergent_type(div): return div" type approach. I'm not sure it's a good idea to combine it with the existing Type::normalized function. That function transforms types extensively and we never use it on types that we plan to persist, it's only used for checking type equivalence.
Parts not directly related to this PR have been moved to #20566, which aims to make recursive type inference converge more generally.
The handling of recursive type inference in this PR should be replaced with something more sophisticated, but I think it's best to land this PR first and complete it in #20566.
Now we have proper cycle handling, Liskov checks, and type-of-self. I think it's a good time to reboot this PR.
It appears that abnormal memory consumption was occurring during the scipy inspection and ty was killed.
The profiling result seem to suggest that IntersectionBuilder is a hotspot.
In particular, cloning and dropping IntersectionBuilder take a long time and huge amounts of memory.
Hmm, in fact, this is a result of fixed-point iterations not converging and the intersection type growing without bound?
The handling of unions in IntersectionBuilder::add_positive_impl seems to exponentially increase the number of intersections, which seems inherently problematic?
mypy_primer: https://github.com/astral-sh/ruff/pull/17371#issuecomment-2799694845 codspeed: https://github.com/astral-sh/ruff/pull/17371#issuecomment-2993362046 type conformance test: https://github.com/astral-sh/ruff/pull/17371#issuecomment-3145365663 ruff_ecosystem: https://github.com/astral-sh/ruff/pull/17371#issuecomment-3044655961
The handling of unions in
IntersectionBuilder::add_positive_implseems to exponentially increase the number ofintersections, which seems inherently problematic?
Yes, it could be problematic, but it's required to keep set-theoretic types in disjunctive normal form, which is valuable, and in most practical cases, unions/intersections don't grow large enough for it to be a problem. We could set some size-maximums with fallback to a less precise type, would have to look at the specific case that causes a blowup. If it's due to fixpoint iteration not converging, then that seems like the key issue to fix.
Fixed IntersectionBuilder to not have multiple identical InnerIntersectionBuilders.
The pydantic result is interesting. It might be worth breaking out as a separate PR.