-
-
Notifications
You must be signed in to change notification settings - Fork 3k
Closed
Labels
bugmypy got something wrongmypy got something wrongtopic-join-v-unionUsing join vs. using unionsUsing join vs. using unions
Description
Bug Report
When doing narrowing of a class attribute with a particular type shape A | B | None, the type of the attribute becomes object after the narrowing condition chain.
To Reproduce
The following is the most minimal reproduction I was able to create.
class A: pass
class B: pass
class C:
attr: A | B | None
c = C()
if c.attr is None: pass
elif isinstance(c.attr, A): pass
elif isinstance(c.attr, B): pass # Optional line - no difference if removed
reveal_type(c.attr)Expected Behavior
Revealed type is A | B | None.
Actual Behavior
Revealed type is object.
I made some additional tests:
pyrightgivesA | B | None(good).- Doing
x = c.xand then doing the narrowing andreveal_typeonattrgivesA | B | None(good). - Replacing the
NonewithA | B | DgivesA | B | D(good). Also if I replaceif isinstance(c.attr, D)withif type(c.attr) is D(good). So theNoneseems essential. - With just
attr: A | None, givesA | None(good). So more than one type besides theNoneseems essential. - Changing the
elif->ifgivesA | B | None(good). So theelifseems essential.
Your Environment
- Mypy version used: master, 0.931, 0.900 (didn't try earlier versions).
- Mypy command-line flags:
--strict. - Mypy configuration options from
mypy.ini(and other config files): - Python version used: 3.9, 3.10
- Operating system and version: Arch Linux
sdeframond
Metadata
Metadata
Assignees
Labels
bugmypy got something wrongmypy got something wrongtopic-join-v-unionUsing join vs. using unionsUsing join vs. using unions