diff options
author | Ralf Gommers <ralf.gommers@gmail.com> | 2021-01-01 13:36:09 +0000 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-01-01 13:36:09 +0000 |
commit | 8275f4e9d32c232f66516351e69c6a09eb7f16d6 (patch) | |
tree | 3bb8d143fc74310b6d5a271a888cebd35886c373 | |
parent | 42100606815dfd5fd18a64fad1a004b577031439 (diff) | |
parent | f2f1867cb35e0b613a6b3f9dacd49dfbfa1cda5c (diff) | |
download | numpydoc-8275f4e9d32c232f66516351e69c6a09eb7f16d6.tar.gz |
Merge pull request #295 from rossbar/xref_conf
ENH: Add configuration option for parameter cross-referencing
-rw-r--r-- | doc/install.rst | 16 | ||||
-rw-r--r-- | numpydoc/docscrape_sphinx.py | 6 | ||||
-rw-r--r-- | numpydoc/tests/test_xref.py | 106 | ||||
-rw-r--r-- | numpydoc/xref.py | 26 |
4 files changed, 144 insertions, 10 deletions
diff --git a/doc/install.rst b/doc/install.rst index 46b26f8..d80e7a7 100644 --- a/doc/install.rst +++ b/doc/install.rst @@ -76,14 +76,26 @@ numpydoc_xref_aliases : dict This option depends on the ``numpydoc_xref_param_type`` option being ``True``. -numpydoc_xref_ignore : set - Words not to cross-reference. Most likely, these are common words +numpydoc_xref_ignore : set or ``"all"`` + How to handle terms not in ``numpydoc_xref_aliases`` when + ``numpydoc_xref_aliases=True``. The value can either be a ``set`` + containing terms to ignore, or ``"all"``. In the former case, the set + contains words not to cross-reference. Most likely, these are common words used in parameter type descriptions that may be confused for classes of the same name. For example:: numpydoc_xref_ignore = {'type', 'optional', 'default'} The default is an empty set. + + If the ``numpydoc_xref_ignore="all"``, then all unrecognized terms are + ignored, i.e. terms not in ``numpydoc_xref_aliases`` are *not* wrapped in + ``:obj:`` roles. + This configuration parameter may be useful if you only want create + cross references for a small number of terms. In this case, including the + desired cross reference mappings in ``numpydoc_xref_aliases`` and setting + ``numpydoc_xref_ignore="all"`` is more convenient than explicitly listing + terms to ignore in a set. numpydoc_edit_link : bool .. deprecated:: edit your HTML template instead diff --git a/numpydoc/docscrape_sphinx.py b/numpydoc/docscrape_sphinx.py index b6f5754..38a49ba 100644 --- a/numpydoc/docscrape_sphinx.py +++ b/numpydoc/docscrape_sphinx.py @@ -73,7 +73,8 @@ class SphinxDocString(NumpyDocString): param_type = make_xref( param_type, self.xref_aliases, - self.xref_ignore) + self.xref_ignore + ) if param.name: out += self._str_indent([named_fmt % (param.name.strip(), param_type)]) @@ -213,7 +214,8 @@ class SphinxDocString(NumpyDocString): param_type = make_xref( param_type, self.xref_aliases, - self.xref_ignore) + self.xref_ignore + ) parts.append(param_type) out += self._str_indent([' : '.join(parts)]) diff --git a/numpydoc/tests/test_xref.py b/numpydoc/tests/test_xref.py index 5d16919..aa14970 100644 --- a/numpydoc/tests/test_xref.py +++ b/numpydoc/tests/test_xref.py @@ -102,6 +102,101 @@ dict[tuple(str, str), int] :class:`python:dict`\[:class:`python:tuple`\(:class:`python:str`, :class:`python:str`), :class:`python:int`] """ # noqa: E501 +data_ignore_obj = r""" +(...) array_like, float, optional +(...) :term:`numpy:array_like`, :class:`python:float`, optional + +(2,) ndarray +(2,) :obj:`ndarray <numpy.ndarray>` + +(...,M,N) array_like +(...,M,N) :term:`numpy:array_like` + +(..., M, N) array_like +(..., M, N) :term:`numpy:array_like` + +(float, float), optional +(:class:`python:float`, :class:`python:float`), optional + +1-D array or sequence +1-D :obj:`array <numpy.ndarray>` or :term:`python:sequence` + +array of str or unicode-like +:obj:`array <numpy.ndarray>` of :class:`python:str` or unicode-like + +array_like of float +:term:`numpy:array_like` of :class:`python:float` + +bool or callable +:ref:`bool <python:bltin-boolean-values>` or :func:`python:callable` + +int in [0, 255] +:class:`python:int` in [0, 255] + +int or None, optional +:class:`python:int` or :data:`python:None`, optional + +list of str or array_like +:class:`python:list` of :class:`python:str` or :term:`numpy:array_like` + +sequence of array_like +:term:`python:sequence` of :term:`numpy:array_like` + +str or pathlib.Path +:class:`python:str` or pathlib.Path + +{'', string}, optional +{'', :class:`python:str`}, optional + +{'C', 'F', 'A', or 'K'}, optional +{'C', 'F', 'A', or 'K'}, optional + +{'linear', 'lower', 'higher', 'midpoint', 'nearest'} +{'linear', 'lower', 'higher', 'midpoint', 'nearest'} + +{False, True, 'greedy', 'optimal'} +{:data:`python:False`, :data:`python:True`, 'greedy', 'optimal'} + +{{'begin', 1}, {'end', 0}}, {string, int} +{{'begin', 1}, {'end', 0}}, {:class:`python:str`, :class:`python:int`} + +callable f'(x,*args) +:func:`python:callable` f'(x,*args) + +callable ``fhess(x, *args)``, optional +:func:`python:callable` ``fhess(x, *args)``, optional + +spmatrix (format: ``csr``, ``bsr``, ``dia`` or coo``) +spmatrix (format: ``csr``, ``bsr``, ``dia`` or coo``) + +:ref:`strftime <strftime-strptime-behavior>` +:ref:`strftime <strftime-strptime-behavior>` + +callable or :ref:`strftime <strftime-strptime-behavior>` +:func:`python:callable` or :ref:`strftime <strftime-strptime-behavior>` + +callable or :ref:`strftime behavior <strftime-strptime-behavior>` +:func:`python:callable` or :ref:`strftime behavior <strftime-strptime-behavior>` + +list(int) +:class:`python:list`\(:class:`python:int`) + +list[int] +:class:`python:list`\[:class:`python:int`] + +dict(str, int) +:class:`python:dict`\(:class:`python:str`, :class:`python:int`) + +dict[str, int] +:class:`python:dict`\[:class:`python:str`, :class:`python:int`] + +tuple(float, float) +:class:`python:tuple`\(:class:`python:float`, :class:`python:float`) + +dict[tuple(str, str), int] +:class:`python:dict`\[:class:`python:tuple`\(:class:`python:str`, :class:`python:str`), :class:`python:int`] +""" # noqa: E501 + xref_ignore = {'or', 'in', 'of', 'default', 'optional'} @@ -111,3 +206,14 @@ xref_ignore = {'or', 'in', 'of', 'default', 'optional'} ) def test_make_xref(param_type, expected_result): assert make_xref(param_type, xref_aliases, xref_ignore) == expected_result + +@pytest.mark.parametrize( + ('param_type', 'expected_result'), + [tuple(s.split('\n')) for s in data_ignore_obj.strip().split('\n\n')] +) +def test_make_xref_ignore_unknown(param_type, expected_result): + assert make_xref(param_type, xref_aliases, xref_ignore="all") == expected_result + +def test_xref_ignore_is_all(): + with pytest.raises(TypeError, match="must be a set or 'all'"): + make_xref("array_like", xref_aliases, xref_ignore="foo") diff --git a/numpydoc/xref.py b/numpydoc/xref.py index 7c6612e..7e98b96 100644 --- a/numpydoc/xref.py +++ b/numpydoc/xref.py @@ -106,8 +106,11 @@ def make_xref(param_type, xref_aliases, xref_ignore): xref_aliases : dict Mapping used to resolve common abbreviations and aliases to fully qualified names that can be cross-referenced. - xref_ignore : set - Words not to cross-reference. + xref_ignore : set or "all" + A set containing words not to cross-reference. Instead of a set, the + string 'all' can be given to ignore all unrecognized terms. + Unrecognized terms include those that are not in `xref_aliases` and + are not already wrapped in a reST role. Returns ------- @@ -115,17 +118,29 @@ def make_xref(param_type, xref_aliases, xref_ignore): Text with fully-qualified names and terms that may be wrapped in a ``:obj:`` role. """ + ignore_set = xref_ignore + wrap_unknown = True + if isinstance(xref_ignore, str): + if xref_ignore.lower() == "all": + wrap_unknown = False + ignore_set = set() + else: + raise TypeError( + "xref_ignore must be a set or 'all', got {}".format(xref_ignore) + ) + if param_type in xref_aliases: link, title = xref_aliases[param_type], param_type param_type = link else: link = title = param_type - if QUALIFIED_NAME_RE.match(link) and link not in xref_ignore: + if QUALIFIED_NAME_RE.match(link) and link not in ignore_set: if link != title: return ':obj:`%s <%s>`' % (title, link) - else: + if wrap_unknown: return ':obj:`%s`' % link + return link def _split_and_apply_re(s, pattern): """ @@ -141,8 +156,7 @@ def make_xref(param_type, xref_aliases, xref_ignore): if pattern.match(tok): results.append(tok) else: - res = make_xref( - tok, xref_aliases, xref_ignore) + res = make_xref(tok, xref_aliases, xref_ignore) # Opening brackets immediately after a role is # bad markup. Detect that and add backslash. # :role:`type`( to :role:`type`\( |