This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: doctest doesn't allow duck-typing callables
Type: enhancement Stage: resolved
Components: Library (Lib) Versions: Python 3.5
process
Status: closed Resolution: fixed
Dependencies: Superseder:
Assigned To: Nosy List: Claudiu.Popa, Guido.van.Rossum, ezio.melotti, gvanrossum, michael.foord, pitrou, python-dev, r.david.murray, rhettinger, tim.peters, yselivanov
Priority: normal Keywords: patch

Created on 2014-06-12 20:59 by pitrou, last changed 2022-04-11 14:58 by admin. This issue is now closed.

Files
File name Uploaded Description Edit
ducktest.py pitrou, 2014-06-12 20:59
issue21740.patch Claudiu.Popa, 2014-07-03 10:25 review
Messages (11)
msg220384 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2014-06-12 20:59
doctest uses inspect.isfunction() to detect callable objects on which to detect docstrings. Unfortunately, this prevents running doctests on functions which have been decorated to return other types of callables (for example numba's @jit decorator). In the attached example file, the wrapped "bar" function does not have its doctest executed.

It would be useful for doctest to be more flexible here, although I'm not sure what the exact criterion should be.
msg221039 - (view) Author: Ezio Melotti (ezio.melotti) * (Python committer) Date: 2014-06-19 22:07
Would using callable() instead of inspect.isfunction() be ok?
msg221040 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2014-06-19 22:13
> Ezio Melotti added the comment:
>
> Would using callable() instead of inspect.isfunction() be ok?

I'm not sure, because it would also select classes. I guess we need 
something a bit smarter.
msg221073 - (view) Author: PCManticore (Claudiu.Popa) * (Python triager) Date: 2014-06-20 08:08
How about using this?

diff -r 1e74350dd056 Lib/doctest.py
--- a/Lib/doctest.py    Tue Jun 17 22:27:46 2014 -0500
+++ b/Lib/doctest.py    Fri Jun 20 11:08:00 2014 +0300
@@ -984,7 +984,8 @@
             for valname, val in obj.__dict__.items():
                 valname = '%s.%s' % (name, valname)
                 # Recurse to functions & classes.
-                if ((inspect.isroutine(val) or inspect.isclass(val)) and
+
+                if ((inspect.isroutine(inspect.unwrap(val)) or inspect.isclass(val)) and
                     self._from_module(module, val)):
                     self._find(tests, val, valname, module, source_lines,
                                globs, seen)

This seems to work for the given example and if the decorator uses update_wrapper or @wraps.
msg221145 - (view) Author: Raymond Hettinger (rhettinger) * (Python committer) Date: 2014-06-21 02:18
> I'm not sure, because it would also select classes. 

Is there any reason to preclude classes?  They could reasonably have docstrings that contain doctests.
msg221917 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2014-06-29 23:31
>> I'm not sure, because it would also select classes.
>
> Is there any reason to preclude classes?  They could reasonably have docstrings that contain doctests.

I don't know. I just didn't want to change doctest behaviour too much, 
but if people more knowledgeable than me about it feel it's ok, then all 
the better.
msg221926 - (view) Author: Guido van Rossum (Guido.van.Rossum) Date: 2014-06-30 00:14
Class doctests are already supported separately, see https://docs.python.org/3/library/doctest.html#which-docstrings-are-examined
msg222167 - (view) Author: PCManticore (Claudiu.Popa) * (Python triager) Date: 2014-07-03 10:25
Here's a test patch which uses inspect.unwrap. Unfortunately, I can't test with numba, so I don't know if it works for that, but any decorated function which uses `functools.update_wrapper` or `wraps` should be detected by doctest.
msg232324 - (view) Author: Roundup Robot (python-dev) (Python triager) Date: 2014-12-08 20:00
New changeset d22ca7496c54 by Yury Selivanov in branch 'default':
Issue #21740: Support wrapped callables in pydoc. Patch by Claudiu Popa.
https://hg.python.org/cpython/rev/d22ca7496c54
msg232325 - (view) Author: Yury Selivanov (yselivanov) * (Python committer) Date: 2014-12-08 20:01
Thank you for the patch, Claudiu!
msg232688 - (view) Author: Roundup Robot (python-dev) (Python triager) Date: 2014-12-15 22:47
New changeset 12ef799a9a51 by Zachary Ware in branch 'default':
Issue #21740: Fix module name in NEWS entry.
https://hg.python.org/cpython/rev/12ef799a9a51
History
Date User Action Args
2022-04-11 14:58:04adminsetgithub: 65939
2021-10-23 21:13:06yaubisetnosy: - yaubi
2014-12-15 22:47:51python-devsetmessages: + msg232688
2014-12-08 20:01:17yselivanovsetstatus: open -> closed

nosy: + yselivanov
messages: + msg232325

resolution: fixed
stage: patch review -> resolved
2014-12-08 20:00:44python-devsetnosy: + python-dev
messages: + msg232324
2014-08-25 09:01:35Claudiu.Popasetstage: needs patch -> patch review
2014-07-29 01:22:32yaubisetnosy: + yaubi
2014-07-03 10:25:35Claudiu.Popasetfiles: + issue21740.patch
keywords: + patch
messages: + msg222167
2014-06-30 00:14:05Guido.van.Rossumsetnosy: + Guido.van.Rossum
messages: + msg221926
2014-06-29 23:31:08pitrousetmessages: + msg221917
2014-06-21 02:18:09rhettingersetmessages: + msg221145
2014-06-20 08:08:56Claudiu.Popasetnosy: + Claudiu.Popa
messages: + msg221073
2014-06-19 22:13:34pitrousetmessages: + msg221040
2014-06-19 22:07:52ezio.melottisetmessages: + msg221039
2014-06-12 20:59:13pitroucreate