facebook / facebook/pyrefly

Literal tuples as iterator in a list/generator passed to tuple constructor show as not assignable to return type with fixed length

Open
#2,994 1 comment 1 reaction 0 assignees View on GitHub
typechecking
Dominant language
Rust
Stars
7k
Forks
516
PR merge metrics
No merged PRs in 30d

Description

### Describe the Bug

Pyrefly gives no errors for this:
```py
def foo() -> tuple[tuple[int, ...], ...]:
first = (1, 2, 3)
second = (4, 5, 6)

return tuple((*items,) for items in (first, second))
```

but this:
```py
def foo() -> tuple[tuple[int, ...], tuple[int, ...]]:
first = (1, 2, 3)
second = (4, 5, 6)
return tuple((*items,) for items in (first, second))
```
gives:

```
ERROR Returned type `tuple[tuple[Literal[1, 2, 3, 4, 5, 6], ...], ...]` is not assignable to declared return type `tuple[tuple[int, ...], tuple[int, ...]]` [bad-return]
--> src\qroutes-files\foo.py:5:12
|
1 | def foo() -> tuple[tuple[int, ...], tuple[int, ...]]:
| --------------------------------------- declared return type
2 | first = (1, 2, 3)
3 | second = (4, 5, 6)
4 |
5 | return tuple((*items,) for items in (first, second))
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
INFO 1 error
```
gives an error, even though the return value will always have length 2.

Similarly, for this case:
```py
def bar(lines: tuple[str, ...]) -> tuple[tuple[str, ...], tuple[str, ...]]:
first, second = lines[0], lines[1]

return tuple(("baz", *items) for items in (first, second))
```

pyrefly gives
```
ERROR Returned type `tuple[tuple[Literal['baz'], *tuple[str, ...]], ...]` is not assignable to declared return type `tuple[tuple[str, ...], tuple[str, ...]]` [bad-return]
--> src\qroutes-files\foo.py:11:12
|
8 | def bar(lines: tuple[str, ...]) -> tuple[tuple[str, ...], tuple[str, ...]]:
| --------------------------------------- declared return type
9 | first, second = lines[0], lines[1]
10 |
11 | return tuple(("baz", *items) for items in (first, second))
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
INFO 1 error
```

even though again the length of the tuple guarantees the return value will always have length 2.

This means your only option is to relax the type annotation to remove the pyrefly error, even though the stricter annotation was valid.

### Sandbox Link

_No response_

### (Only applicable for extension issues) IDE Information

_No response_

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.