https://github.com/python/cpython/commit/ff422bd1c1cde44ca19fdf4d98a5ca55d356bc1e
commit: ff422bd1c1cde44ca19fdf4d98a5ca55d356bc1e
branch: main
author: Jelle Zijlstra <[email protected]>
committer: JelleZijlstra <[email protected]>
date: 2026-05-06T12:00:56-07:00
summary:
gh-141560: Add annotation_format parameter to getfullargspec (#149457)
files:
A Misc/NEWS.d/next/Library/2026-05-06-05-56-59.gh-issue-141560.wlSQaW.rst
M Doc/library/inspect.rst
M Lib/inspect.py
M Lib/test/test_inspect/test_inspect.py
diff --git a/Doc/library/inspect.rst b/Doc/library/inspect.rst
index 4825ac11ae2ee3..d8f9f98589c584 100644
--- a/Doc/library/inspect.rst
+++ b/Doc/library/inspect.rst
@@ -1189,7 +1189,7 @@ Classes and functions
times.
-.. function:: getfullargspec(func)
+.. function:: getfullargspec(func, *, annotation_format=Format.VALUE)
Get the names and default values of a Python function's parameters. A
:term:`named tuple` is returned:
@@ -1219,6 +1219,14 @@ Classes and functions
APIs. This function is retained primarily for use in code that needs to
maintain compatibility with the Python 2 ``inspect`` module API.
+ A member of the
+ :class:`annotationlib.Format` enum can be passed to the
+ *annotation_format* parameter to control the format of the returned
+ annotations. For example, use
+ ``annotation_format=annotationlib.Format.STRING`` to return annotations in
string
+ format. Note that with the default ``VALUE`` format, creation of some
argspecs
+ may raise an exception.
+
.. versionchanged:: 3.4
This function is now based on :func:`signature`, but still ignores
``__wrapped__`` attributes and includes the already bound first
@@ -1236,6 +1244,9 @@ Classes and functions
order of keyword-only parameters as of version 3.7, although in practice
this order had always been preserved in Python 3.
+ .. versionchanged:: next
+ The *annotation_format* parameter was added.
+
.. function:: getargvalues(frame)
diff --git a/Lib/inspect.py b/Lib/inspect.py
index b1bbdd4c365e3d..a96b3dc954ef0c 100644
--- a/Lib/inspect.py
+++ b/Lib/inspect.py
@@ -1254,11 +1254,10 @@ def getargs(co):
FullArgSpec = namedtuple('FullArgSpec',
'args, varargs, varkw, defaults, kwonlyargs, kwonlydefaults, annotations')
-def getfullargspec(func):
+def getfullargspec(func, *, annotation_format=Format.VALUE):
"""Get the names and default values of a callable object's parameters.
- A tuple of seven things is returned:
- (args, varargs, varkw, defaults, kwonlyargs, kwonlydefaults, annotations).
+ A FullArgSpec namedtuple is returned, which has the following attributes:
'args' is a list of the parameter names.
'varargs' and 'varkw' are the names of the * and ** parameters or None.
'defaults' is an n-tuple of the default values of the last n parameters.
@@ -1266,6 +1265,9 @@ def getfullargspec(func):
'kwonlydefaults' is a dictionary mapping names from kwonlyargs to defaults.
'annotations' is a dictionary mapping parameter names to annotations.
+ The *annotation_format* parameter controls the format of the annotations.
+ See the annotationlib documentation for details.
+
Notable differences from inspect.signature():
- the "self" parameter is always reported, even for bound methods
- wrapper chains defined by __wrapped__ *not* unwrapped automatically
@@ -1291,7 +1293,8 @@ def getfullargspec(func):
follow_wrapper_chains=False,
skip_bound_arg=False,
sigcls=Signature,
- eval_str=False)
+ eval_str=False,
+ annotation_format=annotation_format)
except Exception as ex:
# Most of the times 'signature' will raise ValueError.
# But, it can also raise AttributeError, and, maybe something
diff --git a/Lib/test/test_inspect/test_inspect.py
b/Lib/test/test_inspect/test_inspect.py
index efe9d27e3407ff..9028d42c617fb4 100644
--- a/Lib/test/test_inspect/test_inspect.py
+++ b/Lib/test/test_inspect/test_inspect.py
@@ -1355,9 +1355,10 @@ def assertFullArgSpecEquals(self, routine, args_e,
varargs_e=None,
varkw_e=None, defaults_e=None,
posonlyargs_e=[], kwonlyargs_e=[],
kwonlydefaults_e=None,
- ann_e={}):
+ ann_e={},
+ annotation_format=Format.VALUE):
args, varargs, varkw, defaults, kwonlyargs, kwonlydefaults, ann = \
- inspect.getfullargspec(routine)
+ inspect.getfullargspec(routine,
annotation_format=annotation_format)
self.assertEqual(args, args_e)
self.assertEqual(varargs, varargs_e)
self.assertEqual(varkw, varkw_e)
@@ -1390,6 +1391,19 @@ def test_getfullargspec(self):
kwonlyargs_e=['e', 'f'],
kwonlydefaults_e={'e': 4, 'f': 5})
+ def get_getfullargspec_with_undefined_names_in_annotations(self):
+ def my_func(a: undefined_name):
+ pass
+
+ with self.assertRaises(NameError):
+ inspect.getfullargspec(my_func)
+
+ self.assertFullArgSpecEquals(my_func, ['a'], ann_e={'a':
'undefined_name'},
+ annotation_format=Format.STRING)
+
+ arg_spec = inspect.getfullargspec(my_func,
annotation_format=Format.FORWARDREF)
+ self.assertIsInstance(arg_spec.annotations['a'], ForwardRef)
+
def test_argspec_api_ignores_wrapped(self):
# Issue 20684: low level introspection API must ignore __wrapped__
@functools.wraps(mod.spam)
diff --git
a/Misc/NEWS.d/next/Library/2026-05-06-05-56-59.gh-issue-141560.wlSQaW.rst
b/Misc/NEWS.d/next/Library/2026-05-06-05-56-59.gh-issue-141560.wlSQaW.rst
new file mode 100644
index 00000000000000..7e5432be8b6bde
--- /dev/null
+++ b/Misc/NEWS.d/next/Library/2026-05-06-05-56-59.gh-issue-141560.wlSQaW.rst
@@ -0,0 +1 @@
+Add an *annotation_format* parameter to :func:`inspect.getfullargspec`.
_______________________________________________
Python-checkins mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3//lists/python-checkins.python.org
Member address: [email protected]