From ddcf0fea7a68d9f826ed863588ecc494b11d83a4 Mon Sep 17 00:00:00 2001 From: Ross Barnowski Date: Wed, 28 Sep 2022 11:21:38 -0700 Subject: Add cached property support (#433) * TST: Add test case for cached_property. * BUG: Fix detection of cached_property attrs. Co-authored-by: Tirth Patel * Wrap cached_property import in try/except for Python 3.7. Co-authored-by: Tirth Patel --- numpydoc/docscrape.py | 9 ++++++++- numpydoc/tests/test_docscrape.py | 21 +++++++++++++++++++++ 2 files changed, 29 insertions(+), 1 deletion(-) diff --git a/numpydoc/docscrape.py b/numpydoc/docscrape.py index 9496f9d..e5c07f5 100644 --- a/numpydoc/docscrape.py +++ b/numpydoc/docscrape.py @@ -12,6 +12,13 @@ import copy import sys +# TODO: Remove try-except when support for Python 3.7 is dropped +try: + from functools import cached_property +except ImportError: # cached_property added in Python 3.8 + cached_property = property + + def strip_blank_lines(l): "Remove leading and trailing blank lines from a list of lines" while l and not l[0].strip(): @@ -706,7 +713,7 @@ class ClassDoc(NumpyDocString): not name.startswith("_") and ( func is None - or isinstance(func, property) + or isinstance(func, (property, cached_property)) or inspect.isdatadescriptor(func) ) and self._is_show_member(name) diff --git a/numpydoc/tests/test_docscrape.py b/numpydoc/tests/test_docscrape.py index 049d2a2..227f872 100644 --- a/numpydoc/tests/test_docscrape.py +++ b/numpydoc/tests/test_docscrape.py @@ -1,6 +1,7 @@ from collections import namedtuple from copy import deepcopy import re +import sys import textwrap import warnings @@ -1624,6 +1625,26 @@ def test__error_location_no_name_attr(): nds._error_location(msg=msg) +@pytest.mark.skipif( + sys.version_info < (3, 8), reason="cached_property was added in 3.8" +) +def test_class_docstring_cached_property(): + """Ensure that properties marked with the `cached_property` decorator + are listed in the Methods section. See gh-432.""" + from functools import cached_property + + class Foo: + _x = [1, 2, 3] + + @cached_property + def val(self): + return self._x + + class_docstring = get_doc_object(Foo) + assert len(class_docstring["Attributes"]) == 1 + assert class_docstring["Attributes"][0].name == "val" + + if __name__ == "__main__": import pytest -- cgit v1.2.1