Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions src/autodoc2/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ class RenderConfig:
hidden_objects: set[t.Literal["undoc", "dunder", "private", "inherited"]]
hidden_regexes: list[re.Pattern[str]]
deprecated_module_regexes: list[re.Pattern[str]]
no_index: bool
module_summary: bool
class_docstring: t.Literal["merge", "both"]
class_inheritance: bool
Expand Down Expand Up @@ -386,6 +387,15 @@ class Config:
},
)

no_index: bool = dc.field(
default=False,
metadata={
"help": "Do not generate a cross-reference index.",
"sphinx_type": (bool,),
"category": "render",
},
)

deprecated_module_regexes: list[t.Pattern[str]] = dc.field(
default_factory=list,
metadata={
Expand Down Expand Up @@ -508,6 +518,7 @@ def to_render_config(self, pkg_index: int | None) -> RenderConfig:
skip_module_regexes=self.skip_module_regexes,
hidden_objects=self.hidden_objects,
hidden_regexes=self.hidden_regexes,
no_index=self.no_index,
deprecated_module_regexes=self.deprecated_module_regexes,
module_summary=self.module_summary,
class_docstring=self.class_docstring,
Expand All @@ -529,6 +540,7 @@ def to_render_config(self, pkg_index: int | None) -> RenderConfig:
hidden_regexes=self.hidden_regexes
if pkg.hidden_regexes is None
else pkg.hidden_regexes,
no_index=self.no_index,
deprecated_module_regexes=self.deprecated_module_regexes
if pkg.deprecated_module_regexes is None
else pkg.deprecated_module_regexes,
Expand Down
4 changes: 3 additions & 1 deletion src/autodoc2/render/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -213,7 +213,9 @@ def is_module_deprecated(self, item: ItemData) -> bool:
for p in self.config.deprecated_module_regexes
)

# TODO allow for adding :noindex:
def no_index(self, item: ItemData) -> bool:
"""Whether this item should be excluded from search engines."""
return self.config.no_index

def show_module_summary(self, item: ItemData) -> bool:
"""Whether to show a summary for this module/package."""
Expand Down
20 changes: 14 additions & 6 deletions src/autodoc2/render/myst_.py
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,8 @@ def render_package(self, item: ItemData) -> t.Iterable[str]:
yield ""

yield f"```{{py:module}} {full_name}"
if self.no_index(item):
yield ":noindex:"
if self.is_module_deprecated(item):
yield ":deprecated:"
yield from ["```", ""]
Expand Down Expand Up @@ -184,6 +186,8 @@ def render_function(self, item: ItemData) -> t.Iterable[str]:

yield f"{backticks}{{py:function}} {sig}"
yield f":canonical: {item['full_name']}"
if self.no_index(item):
yield ":noindex:"
# TODO overloads
if "async" in item.get("properties", []):
yield ":async:"
Expand Down Expand Up @@ -217,12 +221,10 @@ def render_class(self, item: ItemData) -> t.Iterable[str]:
# note, here we can cannot yield by line,
# because we need to look ahead to know the length of the backticks

lines: list[str] = []

lines += [
f":canonical: {item['full_name']}",
"",
]
lines: list[str] = [f":canonical: {item['full_name']}"]
if self.no_index(item):
lines += [":noindex:"]
lines += [""]

# TODO overloads

Expand Down Expand Up @@ -276,6 +278,8 @@ def render_property(self, item: ItemData) -> t.Iterable[str]:
short_name = item["full_name"].split(".")[-1]
yield f"{backticks}{{py:property}} {short_name}"
yield f":canonical: {item['full_name']}"
if self.no_index(item):
yield ":noindex:"
for prop in ("abstractmethod", "classmethod"):
if prop in item.get("properties", []):
yield f":{prop}:"
Expand Down Expand Up @@ -305,6 +309,8 @@ def render_method(self, item: ItemData) -> t.Iterable[str]:

yield f"{backticks}{{py:method}} {sig}"
yield f":canonical: {item['full_name']}"
if self.no_index(item):
yield ":noindex:"
# TODO overloads
# TODO collect final decorated in analysis
for prop in ("abstractmethod", "async", "classmethod", "final", "staticmethod"):
Expand Down Expand Up @@ -333,6 +339,8 @@ def render_data(self, item: ItemData) -> t.Iterable[str]:

yield f"{backticks}{{py:{item['type']}}} {short_name}"
yield f":canonical: {item['full_name']}"
if self.no_index(item):
yield ":noindex:"
for prop in ("abstractmethod", "classmethod"):
if prop in item.get("properties", []):
yield f":{prop}:"
Expand Down
12 changes: 12 additions & 0 deletions src/autodoc2/render/rst_.py
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,8 @@ def render_package(self, item: ItemData) -> t.Iterable[str]:
yield from [line, "=" * len(line), ""]

yield f".. py:module:: {full_name}"
if self.no_index(item):
yield " :noindex:"
if self.is_module_deprecated(item):
yield " :deprecated:"
yield from ["", ""]
Expand Down Expand Up @@ -171,6 +173,8 @@ def render_function(self, item: ItemData) -> t.Iterable[str]:

yield f".. py:function:: {sig}"
yield f" :canonical: {item['full_name']}"
if self.no_index(item):
yield " :noindex:"
# TODO overloads
if "async" in item.get("properties", []):
yield " :async:"
Expand Down Expand Up @@ -205,6 +209,8 @@ def render_class(self, item: ItemData) -> t.Iterable[str]:

yield f".. py:{item['type']}:: {sig}"
yield f" :canonical: {item['full_name']}"
if self.no_index(item):
yield " :noindex:"
yield ""

# TODO overloads
Expand Down Expand Up @@ -255,6 +261,8 @@ def render_property(self, item: ItemData) -> t.Iterable[str]:
short_name = item["full_name"].split(".")[-1]
yield f".. py:property:: {short_name}"
yield f" :canonical: {item['full_name']}"
if self.no_index(item):
yield " :noindex:"
for prop in ("abstractmethod", "classmethod"):
if prop in item.get("properties", []):
yield f" :{prop}:"
Expand Down Expand Up @@ -283,6 +291,8 @@ def render_method(self, item: ItemData) -> t.Iterable[str]:

yield f".. py:method:: {sig}"
yield f" :canonical: {item['full_name']}"
if self.no_index(item):
yield " :noindex:"
# TODO overloads
# TODO collect final decorated in analysis
for prop in ("abstractmethod", "async", "classmethod", "final", "staticmethod"):
Expand Down Expand Up @@ -310,6 +320,8 @@ def render_data(self, item: ItemData) -> t.Iterable[str]:
short_name = item["full_name"].split(".")[-1]
yield f".. py:{item['type']}:: {short_name}"
yield f" :canonical: {item['full_name']}"
if self.no_index(item):
yield " :noindex:"
for prop in ("abstractmethod", "classmethod"):
if prop in item.get("properties", []):
yield f" :{prop}:"
Expand Down
22 changes: 22 additions & 0 deletions tests/test_render.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,28 @@ def test_basic(renderer: RendererBase, extension: str, tmp_path: Path, file_regr
file_regression.check(content, extension=extension)


@pytest.mark.parametrize(
"renderer,extension",
[
(RstRenderer, ".rst"),
(MystRenderer, ".md"),
],
ids=["rst", "myst"],
)
def test_config_options(
renderer: RendererBase, extension: str, tmp_path: Path, file_regression
):
"""Test basic rendering."""
package = build_package(tmp_path)
db = InMemoryDb()
for path, modname in yield_modules(package):
for item in analyse_module(path, modname):
db.add(item)
config = Config(no_index=True)
content = "\n".join(renderer(db, config).render_item(package.name + ".func"))
file_regression.check(content, extension=extension)


@pytest.mark.parametrize(
"with_rebuild",
[True, False],
Expand Down
7 changes: 7 additions & 0 deletions tests/test_render/test_config_options_myst_.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
```{py:function} func(a: str, b: int) -> package.a.c.ac1
:canonical: package.func
:noindex:

This is a function.

```
5 changes: 5 additions & 0 deletions tests/test_render/test_config_options_rst_.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
.. py:function:: func(a: str, b: int) -> package.a.c.ac1
:canonical: package.func
:noindex:

This is a function.