Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Apparent False Positive With Dict Update Method #5849

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

Closed
lvfrazao opened this issue Oct 28, 2018 · 6 comments
Closed

Apparent False Positive With Dict Update Method #5849

lvfrazao opened this issue Oct 28, 2018 · 6 comments
Labels
bug mypy got something wrong false-positive mypy gave an error on correct code priority-2-low topic-runtime-semantics mypy doesn't model runtime semantics correctly topic-usability

Comments

@lvfrazao
Copy link

Please provide more information to help us understand the issue:
When I define a somewhat complex and heterogeneous dictionary (meant to later be converted to JSON) it causes mypy to alert me to errors which I do not believe are valid.

  • Are you reporting a bug, or opening a feature request?

Bug

  • Please insert below the code you are checking with mypy,
    or a mock-up repro if the source is private. We would appreciate
    if you try to simplify your case to a minimal repro.
from typing import Union, Dict

class A(object):
    def __init__(self, user: Dict[str, Union[str, bool, list, Dict[str, Union[bool, list]]]]):
        d1 = {
            'a': user['name'],
        }

        d2 = {
            'c': 3,
        }

        self.d3 = {**d1, **d2}

print(A({'name': 'victor'}).d3)
  • What is the actual behavior/output?
lvrf@LAPTOP-D0LJCLS0:~$ mypy sample_mypy_code.py
sample_mypy_code.py:13: error: Argument 1 to "update" of "dict" has incompatible type "Dict[str, int]"; expected "Mapping[str, Union[str, bool, List[Any], Dict[str, Union[bool, List[Any]]]]]"

Note, this behaviour only occurs when the 'user' input is typed.

  • What is the behavior/output you expect?

I would expect there to be no error for this operation.

  • What are the versions of mypy and Python you are using?
    Do you see the same issue after installing mypy from Git master?

mypy version 0.641

  • What are the mypy flags you are using? (For example --strict-optional)

No flags

@lvfrazao
Copy link
Author

I would also appreciate any tips that anyone has on how to properly type annotate highly heterogeneous dictionaries to be used for the purpose of interacting with REST APIs.

@ilevkivskyi
Copy link
Member

ilevkivskyi commented Oct 28, 2018

I would also appreciate any tips that anyone has on how to properly type annotate highly heterogeneous dictionaries to be used for the purpose of interacting with REST APIs.

https://mypy.readthedocs.io/en/latest/more_types.html#typeddict

The issue itself is valid, and similar to how mypy overreacts to concatenating lists with different types, the latter can be just fixed in typeshed, while this one might require some special-casing. Btw, have you tried giving an explicit annotation to self.d3?

@ilevkivskyi ilevkivskyi added bug mypy got something wrong priority-2-low topic-usability false-positive mypy gave an error on correct code labels Oct 28, 2018
@lvfrazao
Copy link
Author

Thanks, typeddict looks very promising. I just tried giving self.d3 an explicit annotation and it appears to not make a difference (same error pops up when I run mypy).

@sirosen
Copy link

sirosen commented Mar 12, 2021

I just came across an interesting variant of this error:

class A:
    foo: typing.Dict[str, typing.Union[int, str]] = {"a": 1}

class B(A):
    # incompatible type "Dict[str, Union[int, str]]"; expected "Mapping[str, str]"
    foo = {"b": "c", **A.foo}

I assume that what's happening is that the type of the RHS of that assignment is being resolved before mypy is aware that B.foo should have the same type as A.foo.

This can be fixed by annotating foo. But I think this is something of a problem for libraries which offer inheritance as part of their interface. If a 3rd party developer inherits from A, they have to annotate foo if they override it.

@jdferreira
Copy link

I've stumbled upon the same issue.

class Question(typing.TypedDict):
    id: str
    body: str

question: Question = {
    'id': 'something',
    'body': 'something else',
}

processed = {
    **question,
    'documents': []
}

Hinting with processed: dict seems to silence the warning. I think this solves the issue, but it would be awesome if mypy could derive the type of processed to be typing.TypedDict('<something...>', id=str, body=str, document=str). I don't know if mypy is capable of doing that, or if this type of inference has precedents, though.

@erictraut
Copy link

This bug appears to have been fixed. The latest version of mypy doesn't emit an error for any of the above code samples.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug mypy got something wrong false-positive mypy gave an error on correct code priority-2-low topic-runtime-semantics mypy doesn't model runtime semantics correctly topic-usability
Projects
None yet
Development

No branches or pull requests

6 participants