Skip to content

Literal pattern matching #17303

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
miroslavbel opened this issue May 30, 2024 · 3 comments
Closed

Literal pattern matching #17303

miroslavbel opened this issue May 30, 2024 · 3 comments

Comments

@miroslavbel
Copy link

I hope I haven't made a mistake by asking here instead of in the mypy repository.

Is there a rationale for the discrepancy in the types in this two cases? In the first case (if_stmt), reveal_type correctly identifies the types, while in the second case (match_stmt), None seemingly appears out of nowhere. As I understand, is the issue related to type narrowing?

Code

gist, mypy-playground

from typing import Literal, TypedDict, Union, reveal_type


IntArrayElements = TypedDict("IntArrayElements", {"elements": list[int]})

IntArrayStruct = TypedDict(
    "IntArrayStruct",
    {"data": IntArrayElements, "type": Literal["INT_ARRAY"]},
)
NoneStruct = TypedDict(
    "NoneStruct",
    {"data": None, "type": Literal["NONE"]},
)


response: list[Union[IntArrayStruct, NoneStruct]] = []



for item in response:
    if item['type'] == 'INT_ARRAY':
        _0_data = item["data"]
        reveal_type(_0_data)

        _0_elements = _0_data['elements']
        reveal_type(_0_elements)

    else:
        pass

for item in response:
    match item['type']:
        case 'INT_ARRAY':
            _1_data = item["data"]
            reveal_type(_1_data)         # Line:35

            _1_elements = _1_data['elements']
            reveal_type(_1_elements)     # Line:38

        case _:
            pass

Expected Behavior

...
main.py:35: note: Revealed type is "TypedDict('__main__.IntArrayElements', {'elements': builtins.list[builtins.int]})"
main.py:38: note: Revealed type is "builtins.list[builtins.int]"
...

Actual Behavior

...
main.py:35: note: Revealed type is "Union[TypedDict('__main__.IntArrayElements', {'elements': builtins.list[builtins.int]}), None]"
...
main.py:38: note: Revealed type is "Union[builtins.list[builtins.int], Any]"
...
@hauntsaninja hauntsaninja transferred this issue from python/typeshed May 31, 2024
@hauntsaninja
Copy link
Collaborator

My guess is mypy is missing the tagged union code when handling match statements

@tmke8
Copy link
Contributor

tmke8 commented May 31, 2024

See #15190 and #16286

@hauntsaninja
Copy link
Collaborator

Closing as duplicate of #16286

@hauntsaninja hauntsaninja closed this as not planned Won't fix, can't repro, duplicate, stale May 31, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants