mypyc: cannot query ClassVar members in __init_subclass__ methods of compiled classes
Nobody has claimed this yet.
- Dominant language
- Python
- Stars
- 20.6k
- Forks
- 3.3k
- PR merge metrics
- PR metrics pending
Description
Bug Report
I'm using __init_subclass__ in a class that I'm compiling with mypyc (mostly to avoid using metaclasses), and I'm finding that I'm unable to check the types of the class members within that method. If I annotate a class member with ClassVar[SomeType], then it isn't in available in the class __dir__() yet during __init_subclass__; but if I leave off the ClassVar annotation, then all members are just an instance of <class 'getset_descriptor'>, and I'm unable to differentiate any of them
To Reproduce
compile this module with mypyc:
# test_module.py
from typing import ClassVar
def _print_public_attrs(cls: type) -> None:
for n in dir(cls):
if not n.startswith("_"):
v = getattr(cls, n)
print(n, v, type(v), isinstance(v, SomeDescriptor))
class SomeThing:
pass
class SomeDescriptor:
def __get__(
self, instance: object | None, owner: type | None = None
) -> "SomeDescriptor" | SomeThing:
return SomeThing() if instance is not None else self
class Sup:
def __init_subclass__(cls) -> None:
_print_public_attrs(cls)
class Sub(Sup):
name1 = SomeDescriptor()
name2: ClassVar[SomeDescriptor] = SomeDescriptor()
print("-----")
_print_public_attrs(Sub)
Then import it:
$ python -c "import test_module"
name1 <attribute 'name1' of 'Sub' objects> <class 'getset_descriptor'> False
-----
name1 <attribute 'name1' of 'Sub' objects> <class 'getset_descriptor'> False
name2 <psygnal._test.SomeDescriptor object at 0x1093926e0> <class 'psygnal._test.SomeDescriptor'> True
.... note that name2 (with the ClassVar annotation) isn't available yet during __init_subclass__, but name1 (without the ClassVar annotation) isn't yet an instance of SomeDescriptor during __init_subclass__.
Expected Behavior
I was hoping for some way to check the types of objects on the Sub class during __init_subclass__.
Your Environment
- Mypy version used: mypy 0.991 (compiled: yes)
- Mypy command-line flags:
mypyc test_module.py - Mypy configuration options from
mypy.ini(and other config files): - Python version used: 3.10
thank you!!
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start by reproducing the behavior from test_module.py with the mypyc command shown, focusing on the init_subclass entry point and the ClassVar and descriptor members. Compare the attributes visible during subclass creation with those visible after import; done means the issue's expected ability to distinguish the class members is supported or its limitation is clearly resolved.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- python
- Domain
- compilers
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 38/100