You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
fromtypingimportNamedTuplefromtyping_extensionsimportreveal_typeclassFoo(NamedTuple): passdefprint_foo(foo: Foo): passdefbroken_match(some: Foo|None):
reveal_type(some) # Union[Tuple[, fallback=__main__.Foo], None]matchsome:
caseFoo() asfoo:
# Uncommenting this works with *any* Foo definition#foo = somereveal_type(foo) # __main__.Fooreveal_type(some) # Tuple[, fallback=__main__.Foo]reveal_type(Foo()) # Tuple[, fallback=__main__.Foo]reveal_type(print_foo) # def (foo: Tuple[, fallback=__main__.Foo]) -> Any# Errors with: Argument 1 to "print_foo" has incompatible type "Foo"; expected "Foo"print_foo(foo)
case_:
assertFalse, "nevermind"
Expected Behavior
foo should reveal whatever type Foo() reveals, and this program should type check successfully.
The program type checks if I do any of the following changes:
Assign foo = some inside the case body (everything is Tuple[, fallback=__main__.Foo])
Define Foo as plain class class Foo: pass (everything is __main__.Foo)
Remove the union, i.e. type the arg as some: Foo rather than some: Foo | None
Actual Behavior
main.py:15: note: Revealed type is "Union[Tuple[, fallback=__main__.Foo], None]"
main.py:21: note: Revealed type is "__main__.Foo"
main.py:22: note: Revealed type is "Tuple[, fallback=__main__.Foo]"
main.py:24: note: Revealed type is "Tuple[, fallback=__main__.Foo]"
main.py:25: note: Revealed type is "def (foo: Tuple[, fallback=__main__.Foo]) -> Any"
main.py:28: error: Argument 1 to "print_foo" has incompatible type "Foo"; expected "Foo" [arg-type]
Found 1 error in 1 file (checked 1 source file)
The fact it has the same name in the error is particularly confusing.
Bug Report
When matching on a union between a named tuple and something else, class/as pattern binds to a type different than the named tuple.
That is, the body of
case Foo() as foo:
will produce different values forreveal_type(Foo())
andreveal_type(foo)
.To Reproduce
Playground link. Here for clarity:
Expected Behavior
foo
should reveal whatever typeFoo()
reveals, and this program should type check successfully.The program type checks if I do any of the following changes:
foo = some
inside thecase
body (everything isTuple[, fallback=__main__.Foo]
)Foo
as plain classclass Foo: pass
(everything is__main__.Foo
)some: Foo
rather thansome: Foo | None
Actual Behavior
The fact it has the same name in the error is particularly confusing.
Your Environment
See playground.
The text was updated successfully, but these errors were encountered: