]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-119180: Updates to PEP 649/749 docs (#134640)
authorJelle Zijlstra <jelle.zijlstra@gmail.com>
Mon, 26 May 2025 15:35:04 +0000 (08:35 -0700)
committerGitHub <noreply@github.com>
Mon, 26 May 2025 15:35:04 +0000 (08:35 -0700)
- Mention (again) that `type.__annotations__` is unsafe. It is now safe
  when using only classes defined under PEP 649 semantics, but not with
  classes defined using `from __future__ import annotations`.
- Mention that annotations on instances no longer work. There was already
  an issue about this.
- Mention the general changes in the "Porting to Python 3.14" section.
- `annotationlib` was proposed by PEP-749, not PEP-649.

Co-authored-by: Emma Smith <emma@emmatyping.dev>
Co-authored-by: Carol Willing <carolcode@willingconsulting.com>
Doc/reference/datamodel.rst
Doc/whatsnew/3.14.rst

index 005a768f684e2c08c22f01181a44c489ce89ab29..32a2e266262c52267d7e69dde3ab27e54f6a3bd4 100644 (file)
@@ -1228,10 +1228,22 @@ Special attributes
        :attr:`__annotations__ attributes <object.__annotations__>`.
 
        For best practices on working with :attr:`~object.__annotations__`,
-       please see :mod:`annotationlib`. Where possible, use
+       please see :mod:`annotationlib`. Use
        :func:`annotationlib.get_annotations` instead of accessing this
        attribute directly.
 
+       .. warning::
+
+          Accessing the :attr:`!__annotations__` attribute directly
+          on a class object may return annotations for the wrong class, specifically
+          in certain cases where the class, its base class, or a metaclass
+          is defined under ``from __future__ import annotations``.
+          See :pep:`749 <749#pep749-metaclasses>` for details.
+
+          This attribute does not exist on certain builtin classes. On
+          user-defined classes without ``__annotations__``, it is an
+          empty dictionary.
+
        .. versionchanged:: 3.14
           Annotations are now :ref:`lazily evaluated <lazy-evaluation>`.
           See :pep:`649`.
index 88e52015bdc2b18e5c464cbfff8a2fd6a6c7e139..561d1a8914b50c9e7a9d352902a08cf8e92bf3a4 100644 (file)
@@ -74,7 +74,7 @@ deferred evaluation of annotations (:pep:`649`),
 and a new type of interpreter that uses tail calls.
 
 The library changes include the addition of a new :mod:`!annotationlib` module
-for introspecting and wrapping annotations (:pep:`649`),
+for introspecting and wrapping annotations (:pep:`749`),
 a new :mod:`!compression.zstd` module for Zstandard support (:pep:`784`),
 plus syntax highlighting in the REPL,
 as well as the usual deprecations and removals,
@@ -444,6 +444,10 @@ In particular, do not read annotations directly from the namespace dictionary
 attribute of type objects. Use :func:`annotationlib.get_annotate_from_class_namespace`
 during class construction and :func:`annotationlib.get_annotations` afterwards.
 
+In previous releases, it was sometimes possible to access class annotations from
+an instance of an annotated class. This behavior was undocumented and accidental,
+and will no longer work in Python 3.14.
+
 ``from __future__ import annotations``
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
@@ -2501,6 +2505,11 @@ Changes in the Python API
   See :ref:`above <whatsnew314-typing-union>` for more details.
   (Contributed by Jelle Zijlstra in :gh:`105499`.)
 
+* The runtime behavior of annotations has changed in various ways; see
+  :ref:`above <whatsnew314-pep649>` for details. While most code that interacts
+  with annotations should continue to work, some undocumented details may behave
+  differently.
+
 
 Build changes
 =============