Skip to content

Commit 6bdd854

Browse files
authored
Do not forget that a TypedDict was wrapped in Unpack after a name-defined error occurred. (#17226)
Do not set the `unpacked_kwargs` attribute of `CallableType` to False when visiting a callable of which the `Unpack` wrapper of a `TypedDict` has already been removed. Fixes #17225
1 parent ddcf90d commit 6bdd854

File tree

2 files changed

+39
-1
lines changed

2 files changed

+39
-1
lines changed

mypy/typeanal.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1030,7 +1030,7 @@ def visit_parameters(self, t: Parameters) -> Type:
10301030
def visit_callable_type(self, t: CallableType, nested: bool = True) -> Type:
10311031
# Every Callable can bind its own type variables, if they're not in the outer scope
10321032
with self.tvar_scope_frame():
1033-
unpacked_kwargs = False
1033+
unpacked_kwargs = t.unpack_kwargs
10341034
if self.defining_alias:
10351035
variables = t.variables
10361036
else:

test-data/unit/check-typeddict.test

+38
Original file line numberDiff line numberDiff line change
@@ -3487,3 +3487,41 @@ class A(Generic[T]):
34873487
return self.a(x=1)
34883488
[typing fixtures/typing-full.pyi]
34893489
[builtins fixtures/tuple.pyi]
3490+
3491+
[case testNameUndefinedErrorDoesNotLoseUnpackedKWArgsInformation]
3492+
from typing import overload
3493+
from typing_extensions import TypedDict, Unpack
3494+
3495+
class TD(TypedDict, total=False):
3496+
x: int
3497+
y: str
3498+
3499+
@overload
3500+
def f(self, *, x: int) -> None: ...
3501+
@overload
3502+
def f(self, *, y: str) -> None: ...
3503+
def f(self, **kwargs: Unpack[TD]) -> None:
3504+
z # E: Name "z" is not defined
3505+
3506+
@overload
3507+
def g(self, *, x: float) -> None: ...
3508+
@overload
3509+
def g(self, *, y: str) -> None: ...
3510+
def g(self, **kwargs: Unpack[TD]) -> None: # E: Overloaded function implementation does not accept all possible arguments of signature 1
3511+
z # E: Name "z" is not defined
3512+
3513+
class A:
3514+
def f(self, *, x: int) -> None: ...
3515+
def g(self, *, x: float) -> None: ...
3516+
class B(A):
3517+
def f(self, **kwargs: Unpack[TD]) -> None:
3518+
z # E: Name "z" is not defined
3519+
def g(self, **kwargs: Unpack[TD]) -> None: # E: Signature of "g" incompatible with supertype "A" \
3520+
# N: Superclass: \
3521+
# N: def g(self, *, x: float) -> None \
3522+
# N: Subclass: \
3523+
# N: def g(*, x: int = ..., y: str = ...) -> None
3524+
z # E: Name "z" is not defined
3525+
reveal_type(B.f) # N: Revealed type is "def (self: __main__.B, **kwargs: Unpack[TypedDict('__main__.TD', {'x'?: builtins.int, 'y'?: builtins.str})])"
3526+
B().f(x=1.0) # E: Argument "x" to "f" of "B" has incompatible type "float"; expected "int"
3527+
[builtins fixtures/primitives.pyi]

0 commit comments

Comments
 (0)