Skip to content
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

Odd behavior when creating namedtuple #10954

Open
gemerden opened this issue Aug 9, 2021 · 2 comments
Open

Odd behavior when creating namedtuple #10954

gemerden opened this issue Aug 9, 2021 · 2 comments

Comments

@gemerden
Copy link

gemerden commented Aug 9, 2021

I am writing a descriptor and attempting to annotate using the typing module. I think I have found a bug, but since I am pretty new to mypy I am posting it here. Below is the behavior I encountered:

# test_file.py
from collections import namedtuple

class Snapshot:
    def create_tuple_type(self, name: str):
        self.tuple_type = namedtuple(name, [])  # line 6

def create_tuple_type_1(name: str):
    x = namedtuple(name, [])                    # line 9

def create_tuple_type_2(name: str):
    return namedtuple(name, [])

running: mypy test_file.py prints:

snapshot\tinutest.py:6: error: NamedTuple type as an attribute is not supported
snapshot\tinutest.py:6: error: namedtuple() expects a string literal as the first argument
snapshot\tinutest.py:9: error: namedtuple() expects a string literal as the first argument
Found 3 errors in 1 file (checked 1 source file)

I am confused:

  • what does the first error mean, I am not using NamedTuple (also NamedTuple is not a type, but a function)?
  • I explicitly set name to be a string, why the second and third error (it says 'literal', but there is no reason this would not work, it actually does in practice ;-)?
  • why does create_tuple_type_1 give an error, while create_tuple_type_2 doesn't?

This might more issues, but since they occur so close together, they might be correlated?

@JelleZijlstra
Copy link
Member

The general explanation is that mypy doesn't generally support dynamic creation of types (and namedtuples are types, even if they are created through a function). For every namedtuple class, it wants to be able to figure out the name and fields at compile time.

It's unfortunate that the error message says "NamedTuple" instead of "namedtuple". typing.NamedTuple is the typing-friendly version of collections.namedtuple, but ideally mypy should put the right spelling in its error messages.

@gemerden
Copy link
Author

gemerden commented Aug 12, 2021

If it doesn't support dynamic type creation, shouldn't it ignore it?

namedtuple() expects a string literal as the first argument, this is just not true, and collections.namedtuple is not annotated.

I mean, this still seems very odd to me.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants