Skip to content

Use double quotes in errors related to TypeDict Keys #10352

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 21, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions mypy/messages.py
Original file line number Diff line number Diff line change
Expand Up @@ -2121,11 +2121,11 @@ def make_inferred_type_note(context: Context,


def format_key_list(keys: List[str], *, short: bool = False) -> str:
reprs = [repr(key) for key in keys]
formatted_keys = ['"{}"'.format(key) for key in keys]
td = '' if short else 'TypedDict '
if len(keys) == 0:
return 'no {}keys'.format(td)
elif len(keys) == 1:
return '{}key {}'.format(td, reprs[0])
return '{}key {}'.format(td, formatted_keys[0])
else:
return '{}keys ({})'.format(td, ', '.join(reprs))
return '{}keys ({})'.format(td, ', '.join(formatted_keys))
4 changes: 2 additions & 2 deletions test-data/unit/check-errorcodes.test
Original file line number Diff line number Diff line change
Expand Up @@ -454,9 +454,9 @@ class E(TypedDict):
y: int

a: D = {'x': ''} # E: Incompatible types (expression has type "str", TypedDict item "x" has type "int") [typeddict-item]
b: D = {'y': ''} # E: Extra key 'y' for TypedDict "D" [typeddict-item]
b: D = {'y': ''} # E: Extra key "y" for TypedDict "D" [typeddict-item]
c = D(x=0) if int() else E(x=0, y=0)
c = {} # E: Expected TypedDict key 'x' but found no keys [typeddict-item]
c = {} # E: Expected TypedDict key "x" but found no keys [typeddict-item]
[builtins fixtures/dict.pyi]

[case testErrorCodeCannotDetermineType]
Expand Down
38 changes: 19 additions & 19 deletions test-data/unit/check-typeddict.test
Original file line number Diff line number Diff line change
Expand Up @@ -60,13 +60,13 @@ p = Point({x: 42, 'y': 1337}) # E: Expected TypedDict key to be string literal
[case testCannotCreateTypedDictInstanceWithExtraItems]
from mypy_extensions import TypedDict
Point = TypedDict('Point', {'x': int, 'y': int})
p = Point(x=42, y=1337, z=666) # E: Extra key 'z' for TypedDict "Point"
p = Point(x=42, y=1337, z=666) # E: Extra key "z" for TypedDict "Point"
[builtins fixtures/dict.pyi]

[case testCannotCreateTypedDictInstanceWithMissingItems]
from mypy_extensions import TypedDict
Point = TypedDict('Point', {'x': int, 'y': int})
p = Point(x=42) # E: Missing key 'y' for TypedDict "Point"
p = Point(x=42) # E: Missing key "y" for TypedDict "Point"
[builtins fixtures/dict.pyi]

[case testCannotCreateTypedDictInstanceWithIncompatibleItemType]
Expand Down Expand Up @@ -149,7 +149,7 @@ def foo(x):
# type: (Movie) -> None
pass

foo({}) # E: Missing keys ('name', 'year') for TypedDict "Movie"
foo({}) # E: Missing keys ("name", "year") for TypedDict "Movie"
foo({'name': 'lol', 'year': 2009, 'based_on': 0}) # E: Incompatible types (expression has type "int", TypedDict item "based_on" has type "str")

[builtins fixtures/dict.pyi]
Expand Down Expand Up @@ -871,15 +871,15 @@ Point = TypedDict('Point', {'x': int, 'y': int})
def f(p: Point) -> None:
if int():
p = {'x': 2, 'y': 3}
p = {'x': 2} # E: Missing key 'y' for TypedDict "Point"
p = {'x': 2} # E: Missing key "y" for TypedDict "Point"
p = dict(x=2, y=3)

f({'x': 1, 'y': 3})
f({'x': 1, 'y': 'z'}) # E: Incompatible types (expression has type "str", TypedDict item "y" has type "int")

f(dict(x=1, y=3))
f(dict(x=1, y=3, z=4)) # E: Extra key 'z' for TypedDict "Point"
f(dict(x=1, y=3, z=4, a=5)) # E: Extra keys ('z', 'a') for TypedDict "Point"
f(dict(x=1, y=3, z=4)) # E: Extra key "z" for TypedDict "Point"
f(dict(x=1, y=3, z=4, a=5)) # E: Extra keys ("z", "a") for TypedDict "Point"

[builtins fixtures/dict.pyi]

Expand All @@ -888,15 +888,15 @@ from mypy_extensions import TypedDict

Point = TypedDict('Point', {'x': int, 'y': int})

p1a: Point = {'x': 'hi'} # E: Missing key 'y' for TypedDict "Point"
p1b: Point = {} # E: Missing keys ('x', 'y') for TypedDict "Point"
p1a: Point = {'x': 'hi'} # E: Missing key "y" for TypedDict "Point"
p1b: Point = {} # E: Missing keys ("x", "y") for TypedDict "Point"

p2: Point
p2 = dict(x='bye') # E: Missing key 'y' for TypedDict "Point"
p2 = dict(x='bye') # E: Missing key "y" for TypedDict "Point"

p3 = Point(x=1, y=2)
if int():
p3 = {'x': 'hi'} # E: Missing key 'y' for TypedDict "Point"
p3 = {'x': 'hi'} # E: Missing key "y" for TypedDict "Point"

p4: Point = {'x': 1, 'y': 2}

Expand All @@ -911,7 +911,7 @@ T = TypeVar('T')
def join(x: T, y: T) -> T: return x
ab = join(A(x=1, y=1), B(x=1, y=''))
if int():
ab = {'x': 1, 'z': 1} # E: Expected TypedDict key 'x' but found keys ('x', 'z')
ab = {'x': 1, 'z': 1} # E: Expected TypedDict key "x" but found keys ("x", "z")
[builtins fixtures/dict.pyi]

[case testCannotCreateAnonymousTypedDictInstanceUsingDictLiteralWithMissingItems]
Expand All @@ -923,7 +923,7 @@ T = TypeVar('T')
def join(x: T, y: T) -> T: return x
ab = join(A(x=1, y=1, z=1), B(x=1, y=1, z=''))
if int():
ab = {} # E: Expected TypedDict keys ('x', 'y') but found no keys
ab = {} # E: Expected TypedDict keys ("x", "y") but found no keys
[builtins fixtures/dict.pyi]


Expand Down Expand Up @@ -1044,7 +1044,7 @@ f({})
f({'x': 1})
f({'y': ''})
f({'x': 1, 'y': ''})
f({'x': 1, 'z': ''}) # E: Extra key 'z' for TypedDict "D"
f({'x': 1, 'z': ''}) # E: Extra key "z" for TypedDict "D"
f({'x': ''}) # E: Incompatible types (expression has type "str", TypedDict item "x" has type "int")
[builtins fixtures/dict.pyi]

Expand All @@ -1056,7 +1056,7 @@ reveal_type(D()) # N: Revealed type is "TypedDict('__main__.D', {'x'?: builtins.
reveal_type(D(x=1)) # N: Revealed type is "TypedDict('__main__.D', {'x'?: builtins.int, 'y'?: builtins.str})"
f(D(y=''))
f(D(x=1, y=''))
f(D(x=1, z='')) # E: Extra key 'z' for TypedDict "D"
f(D(x=1, z='')) # E: Extra key "z" for TypedDict "D"
f(D(x='')) # E: Incompatible types (expression has type "str", TypedDict item "x" has type "int")
[builtins fixtures/dict.pyi]

Expand Down Expand Up @@ -1614,9 +1614,9 @@ a.update({'x': 1})
a.update({'x': ''}) # E: Incompatible types (expression has type "str", TypedDict item "x" has type "int")
a.update({'x': 1, 'y': []})
a.update({'x': 1, 'y': [1]})
a.update({'z': 1}) # E: Unexpected TypedDict key 'z'
a.update({'z': 1, 'zz': 1}) # E: Unexpected TypedDict keys ('z', 'zz')
a.update({'z': 1, 'x': 1}) # E: Expected TypedDict key 'x' but found keys ('z', 'x')
a.update({'z': 1}) # E: Unexpected TypedDict key "z"
a.update({'z': 1, 'zz': 1}) # E: Unexpected TypedDict keys ("z", "zz")
a.update({'z': 1, 'x': 1}) # E: Expected TypedDict key "x" but found keys ("z", "x")
d = {'x': 1}
a.update(d) # E: Argument 1 to "update" of "TypedDict" has incompatible type "Dict[str, int]"; expected "TypedDict({'x'?: int, 'y'?: List[int]})"
[builtins fixtures/dict.pyi]
Expand Down Expand Up @@ -1977,7 +1977,7 @@ v = {union: 2} # E: Expected TypedDict key to be string literal
num2: Literal['num']
v = {num2: 2}
bad2: Literal['bad']
v = {bad2: 2} # E: Extra key 'bad' for TypedDict "Value"
v = {bad2: 2} # E: Extra key "bad" for TypedDict "Value"

[builtins fixtures/dict.pyi]
[typing fixtures/typing-typeddict.pyi]
Expand Down Expand Up @@ -2107,5 +2107,5 @@ d[True] # E: TypedDict key must be a string literal; expected one of ('foo')
from mypy_extensions import TypedDict

Foo = TypedDict('Foo', {'camelCaseKey': str})
value: Foo = {} # E: Missing key 'camelCaseKey' for TypedDict "Foo"
value: Foo = {} # E: Missing key "camelCaseKey" for TypedDict "Foo"
[builtins fixtures/dict.pyi]
2 changes: 1 addition & 1 deletion test-data/unit/pythoneval.test
Original file line number Diff line number Diff line change
Expand Up @@ -1120,7 +1120,7 @@ _testTypedDictMappingMethods.py:10: note: Revealed type is "typing.ItemsView[bui
_testTypedDictMappingMethods.py:11: note: Revealed type is "typing.ValuesView[builtins.object]"
_testTypedDictMappingMethods.py:12: note: Revealed type is "TypedDict('_testTypedDictMappingMethods.Cell', {'value': builtins.int})"
_testTypedDictMappingMethods.py:13: note: Revealed type is "builtins.int"
_testTypedDictMappingMethods.py:15: error: Unexpected TypedDict key 'invalid'
_testTypedDictMappingMethods.py:15: error: Unexpected TypedDict key "invalid"
_testTypedDictMappingMethods.py:16: error: Key "value" of TypedDict "Cell" cannot be deleted
_testTypedDictMappingMethods.py:21: note: Revealed type is "builtins.int"

Expand Down