[Python-Dev] Postponed annotations break inspection of dataclasses (original) (raw)

Guido van Rossum guido at python.org
Sat Sep 22 12:41:22 EDT 2018


This is a good catch -- thanks for bringing it up. I'm adding Eric Smith (author of dataclasses) and Ivan Levkivskyi (co-author of typing) as well as Ɓukasz Langa (author of PEP 563) to the thread to see if they have further insights.

Personally I don't think it's feasible to change PEP 563 to use lambdas (if it were even advisable, which would be a long discussion), but I do think we might be able to make small improvements to the dataclasses and/or typing modules to make sure your use case works.

Probably a bugs.python.org issue is a better place to dive into the details than python-dev.

Thanks again,

--Guido (top-poster in chief)

On Sat, Sep 22, 2018 at 8:32 AM David Hagen <david at drhagen.com> wrote:

The new postponed annotations have an unexpected interaction with dataclasses. Namely, you cannot get the type hints of any of the data classes methods.

For example, I have some code that inspects the type parameters of a class's _init_ method. (The real use case is to provide a default serializer for the class, but that is not important here.) _ _from dataclasses import dataclass_ _from typing import gettypehints_ _class Foo:_ _pass_ _@dataclass_ _class Bar:_ _foo: Foo_ _print(gettypehints(Bar._init_))_ _ In Python 3.6 and 3.7, this does what is expected; it prints {'foo':_ _<class '_main_.Foo'>, 'return': <class 'NoneType'>}. However, if in Python 3.7, I add from _future_ import annotations, then this fails with an error: _ _NameError: name 'Foo' is not defined_ _ I know why this is happening. The _init_ method is defined in the dataclasses module which does not have the Foo object in its environment, and the Foo annotation is being passed to dataclass and attached to _init_ as the string "Foo" rather than as the original object Foo, but gettypehints for the new annotations only does a name lookup in the module where _init_ is defined not where the annotation is defined. I know that the use of lambdas to implement PEP 563 was rejected for performance reasons. I could be wrong, but I think this was motivated by variable annotations because the lambda would have to be constructed each time the function body ran. I was wondering if I could motivate storing the annotations as lambdas in class bodies and function signatures, in which the environment is already being captured and is code that usually only runs once.


Python-Dev mailing list Python-Dev at python.org https://mail.python.org/mailman/listinfo/python-dev Unsubscribe: https://mail.python.org/mailman/options/python-dev/guido%40python.org

-- --Guido van Rossum (python.org/~guido) -------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.python.org/pipermail/python-dev/attachments/20180922/a66a20f7/attachment.html>



More information about the Python-Dev mailing list