Skip to content

Fix various bugs in TypeVarTuples with defaults#21544

Open
ilevkivskyi wants to merge 1 commit into
python:masterfrom
ilevkivskyi:tvd-tvt
Open

Fix various bugs in TypeVarTuples with defaults#21544
ilevkivskyi wants to merge 1 commit into
python:masterfrom
ilevkivskyi:tvd-tvt

Conversation

@ilevkivskyi
Copy link
Copy Markdown
Member

Fixes a bunch of TODOs in tests.
Fixes #20449

Couple non-trivial things here:

First, I prohibit (regular) type variables with defaults that appear after a TypeVarTuple. The PEP and the spec are clear that these are ambiguous and invalid. But, because they are ambiguous, we can't simply give the error, since otherwise various parts of code will behave in weirdly inconsistent ways. Therefore, I completely erase ambiguous type variables out of existence, 1984 style.

Second, couple commented-out tests cases suggested that TypeVarTuple defaults should be used in cases where *tuple[()] would be used as a value otherwise, plus Foo[X, Y] and Foo[X, Y, *tuple[()]] should be interpreted differently. I don't see anything about this in the PEP/spec, and I don't like this. I think the default should be used only in cases where Any or Never would be used otherwise.

@github-actions
Copy link
Copy Markdown
Contributor

Diff from mypy_primer, showing the effect of this PR on open source code:

static-frame (https://github.com/static-frame/static-frame)
+ static_frame/core/node_re.py:54: error: Unused "type: ignore" comment  [unused-ignore]
+ static_frame/core/node_re.py:59: error: Unused "type: ignore" comment  [unused-ignore]
+ static_frame/core/node_dt.py:120: error: Unused "type: ignore" comment  [unused-ignore]
+ static_frame/core/node_dt.py:124: error: Unused "type: ignore" comment  [unused-ignore]
+ static_frame/core/node_str.py:93: error: Unused "type: ignore" comment  [unused-ignore]
+ static_frame/core/node_str.py:98: error: Unused "type: ignore" comment  [unused-ignore]

@ilevkivskyi
Copy link
Copy Markdown
Member Author

Not 100% sure what happened with static-frame, but it looks like a clear improvement. Probably caused by the fact that one of the TypeVar values is itself a class generic in a TypeVarTuple with an explicit default.

Copy link
Copy Markdown
Collaborator

@JukkaL JukkaL left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not a full review -- I found a few potential issues.

Comment thread mypy/message_registry.py
'Implicit generic "Any". Use "{}" and specify generic parameters'
)
NO_CYCLIC_DEFAULT: Final = "Cyclic type variable defaults are not supported"
NO_DEFAULT_AFTER_TYPEVAR_TUPLE: Final = "A type variable with default cannot follow TypVarTuple"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Typo: TypVarTuple -> TypeVarTuple

reveal_type(a) # N: Revealed type is "__main__.ClassC2[builtins.str, Unpack[builtins.tuple[builtins.float, ...]]]"
# reveal_type(b) # Revealed type is "__main__.ClassC2[builtins.int, Unpack[builtins.tuple[builtins.float, ...]]]" # TODO
reveal_type(c) # N: Revealed type is "__main__.ClassC2[builtins.int]"
reveal_type(b) # N: Revealed type is "__main__.ClassC2[builtins.int]"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems to lose the default Unpack[builtins.tuple[builtins.float, ...]] for Ts3 -- this is different from the original commented-out expectation.

# reveal_type(b) # Revealed type is "Tuple[builtins.int, Unpack[builtins.tuple[builtins.float, ...]]]" # TODO
reveal_type(c) # N: Revealed type is "tuple[builtins.int]"
reveal_type(a) # N: Revealed type is "tuple[builtins.str, Unpack[builtins.tuple[builtins.float, ...]]]"
reveal_type(b) # N: Revealed type is "tuple[builtins.int]"
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This also loses the default and changes the expectation from the original. Is this intentional?

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

Successfully merging this pull request may close these issues.

The default type set to *Ts for the generic type alias TA doesn't work even though no type arguments are set to TA

2 participants