Open flying-sheep opened 2 years ago
I am not exactly sure if the following is the same bug, but I also have trouble running this with Python 3.8.
Running the following script
#!/usr/bin/env python
from __future__ import annotations
from get_annotations import get_annotations
def function(a: str | int):
pass
print(get_annotations(function, eval_str=True))
yields the exception:
Traceback (most recent call last):
File "annotations.py", line 10, in <module>
print(get_annotations(function, eval_str=True))
File "/home/sph/.virtualenvs/aiida_dev/lib/python3.8/site-packages/get_annotations/__init__.py", line 117, in get_annotations
return_value = {key:
File "/home/sph/.virtualenvs/aiida_dev/lib/python3.8/site-packages/get_annotations/__init__.py", line 118, in <dictcomp>
value if not isinstance(value, str) else eval(value, globals, locals)
File "<string>", line 1, in <module>
TypeError: unsupported operand type(s) for |: 'type' and 'type'
The declaration of the function itself works perfectly fine, due to the from __future__ import annotations
. So not quite sure why this failing in the get_annotations
call.
TypeError: unsupported operand type(s) for |: 'type' and 'type'
This type syntax: str | int
is not supported until Python 3.10. You should use typing.Union
instead
In previous versions, it's just a bitwise or
I think I see where my confusion come from now: it is possible to use str | int
in Python 3.7 and up, as long as from __future__ import annotations
is added, as this enables the postponed evaluation of annotations [PEP 563]. In this case, the type hints are simply stored as strings and not actually evaluated. This is why str | int
becomes "valid" in Python older than 3.10. If the expression is evaluated, it needs support for the new union type syntax of PEP 604, which was released with Python 3.10 as you say. TL:DR my post above can indeed be ignored.
https://github.com/shawwn/get-annotations/blob/8ef2d4e1d9f60a68c9f3a79118e99080ec9f181d/get_annotations/__init__.py#L117-L119
With Python 3.9 and
from __future__ import annotations
, I get adict[str, typing.ForwardRef]
no matter if I specifyeval_str=True
or not.isinstance(value, str)
is of courseFalse
forForwardRef
s …You should setup CI for all supported Python versions to make sure it works!