Skip to content

Enum of a NamedTuple-derived type leads to incompatible type error #1745

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
alexsydell opened this issue Jun 25, 2016 · 5 comments
Closed

Enum of a NamedTuple-derived type leads to incompatible type error #1745

alexsydell opened this issue Jun 25, 2016 · 5 comments
Labels
bug mypy got something wrong topic-named-tuple

Comments

@alexsydell
Copy link

This code:

from typing import NamedTuple
from enum import Enum

Foo = NamedTuple('Foo', [('bar', int)])

class MyEnum(Foo, Enum):
    CONSTANT = Foo(bar=1)

def f(x):
    # type: (MyEnum) -> None
    pass

f(MyEnum.CONSTANT)

leads to:

error: Argument 1 to "f" has incompatible type "test.MyEnum"; expected "MyEnum"
@gvanrossum
Copy link
Member

I know we have plenty of namedtuple-related issues. But does this code serve a real purpose? Enum has a lot of magic, so does namedtuple -- I'm not sure if we should really be required to make sense of this, and what you're trying to accomplishing with that class.

@alexsydell
Copy link
Author

This is a distilled example of a real-life enum I came across in our code. Not going to get into whether or not having such an enum is a good idea, but we have it and I'm getting mypy errors trying to use it as an argument to a function. The main weirdness is that the error is of the form incompatible type: "fully.qualified.path.to.MyEnum"; expected "MyEnum" which seems fishy.

@gvanrossum
Copy link
Member

Note that without the Foo base class you can still access the bar attribute in f() -- use x.value.bar rather than x.bar.

@gnprice
Copy link
Collaborator

gnprice commented Aug 9, 2016

This came up again today -- a user hit an error message just as confusing (and with the same structure) as the one in @alexsydell's report, and after some debugging someone else recognized it as this issue.

In addition to the type-checker issue that we shouldn't be reporting an error here at all, the error message is awfully perplexing and is likely an example of #1582.

@gnprice gnprice added the bug mypy got something wrong label Aug 11, 2016
@gnprice gnprice added this to the 0.5 milestone Aug 11, 2016
@elazarg
Copy link
Contributor

elazarg commented Sep 5, 2016

I believe that this is a result of the special casing of both Enum and NamedTuple. It can be special-cased too at subtypes.py:

        right = self.right
+       if isinstance(right, TupleType) and right.fallback.type.is_enum:
+           return is_subtype(left, right.fallback)
        if isinstance(right, Instance):

I think that this special casing is justified, but I'm not sure.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug mypy got something wrong topic-named-tuple
Projects
None yet
Development

No branches or pull requests

4 participants