Skip to content

literal promotion in inference fails to account for type context #1198

@carljm

Description

@carljm

A similar issue came up in astral-sh/ruff#20360. We now unconditionally promote any literals within the elements of a list/set literal, partly for performance reasons with large list literals. However, this means that we fail to typecheck against literal annotations, e.g.,

# error: Object of type `list[int]` is not assignable to `list[Literal[1, 2, 3]]`
x: list[Literal[1, 2, 3]] = [1, 2, 3]

# error: Object of type `list[str]` is not assignable to `list[LiteralString]`
x: list[LiteralString] = ["a", "b", "c"]

Which is the same issue we currently run into with generic classes:

# error: Object of type `tuple[X[int]]` is not assignable to `tuple[X[Literal[1]]]`
x: tuple[X[Literal[1]]] = (X(1), )

My reading of this issue is that we promote should eagerly promote literals, unless there is an explicit type annotation that would require otherwise? That seems to align with pyright's behavior as well.

@carljm pointed out that this could get tricky with nested types, or even unions:

x: list[int | Literal["a"]] = [1, 2, 3, "a", 4, 5, 6]
reveal_type(x)

Originally posted by @ibraheemdev in #336

Metadata

Metadata

Assignees

Labels

bidirectional inferenceInference of types that takes into account the context of a declared type or expected typegenericsBugs or features relating to ty's generics implementation

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions