Skip to content

Erroneous narrowing for Union including tuples of different lengths #2196

@bcmills

Description

@bcmills

Describe the Bug

def test(x: Union[str, tuple[int, str], tuple[int, str, str]]) -> str:
    if (not isinstance(x, tuple)) or len(x) != 3:
        return "nope"
    reveal_type(x)
    _, _, s = x
    return s

In this code, at the point where the tuple unpacking occurs the parameter x is known to be a tuple of length 3, so narrowing should give it the type tuple[int, str, str].

pyrefly erroneously assigns it the type tuple[int, str] instead:

INFO sandbox.py:6:16-19: revealed type: tuple[int, str] [[reveal-type](https://pyrefly.org/en/docs/error-kinds/#reveal-type)]
ERROR sandbox.py:7:5-12: Cannot unpack tuple[int, str] (of size 2) into 3 values [[bad-unpacking](https://pyrefly.org/en/docs/error-kinds/#bad-unpacking)]
INFO sandbox.py:10:12-38: revealed type: str [[reveal-type](https://pyrefly.org/en/docs/error-kinds/#reveal-type)]

Sandbox Link

https://pyrefly.org/sandbox/?project=N4IgZglgNgpgziAXKOBDAdgEwEYHsAeAdAA4CeS4ATrgLYAEALqcROgOZ0Q3G6UN0AqADroRmGGEbwGACnyI6AVXQRc6ANpwGlADSMArsVjrWDPVsoBdPQ0PHT57Y6uWAlHQC0APjoXEIukDOSRl0XH4IOFYtDABjGDkbOxhXd146WHQ5dwBCAF46AGZ-dCCyukoYW0pSoRAw4hg6gKCAfT123zoC-BbAyurSuBERSoA3GFQoVqZGmQZpGRkAFgAmPTqwXFw6jZBsVEo61NcRYkpTecWV9bpN7d27-cPj1JAdEH0GaDgSckQQABiJTfKAQJh0MD6dCxb5qYaiLASSG8GioBitdD6GjYGCUOQKUzuby%2BbQlMoDfQ1SF1ABy2NxlAUwHwAF9muh3iAyJUwFBSIQGLQoBRgQAFUi8-m%2BDA4Ah0WJqSBsKno1ToQgiYEAZRgMDoAAsGAxiHBEAB6c08iT8wi8NjmmDoc2YXCxODmxXoZWquHOlGUOioMaoaCobCwBVKiAqyhqtR0XDEP2-M6kBgGtQeCaUKIJgp1QqEACMqw5IFZH1QsIgEwAYtAYBQ0Fg8EQyBWgA

(Only applicable for extension issues) IDE Information

No response

Metadata

Metadata

Assignees

Labels

narrowingIssues with narrowing - root cause is usually narrowing, flow handling, or bothtypechecking

Type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions