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
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,7 @@ dmypy.json
# Documentation
/site
index.md
/api/
docs/_build/
docs/api
docs/html
Expand Down
40 changes: 6 additions & 34 deletions docs/src/api.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,46 +61,18 @@ Or document specific classes with `doxygenclass`:

## Rust Example

This is an example of documenting Rust code using sphinx-rust integration.
This is an example of documenting Rust code using sphinxcontrib-rust integration.

### Document a Crate

Use `rust:crate` to document an entire Rust crate:

```{eval-rst}
.. rust:crate:: calculator

```
Unlike the C++ and JavaScript examples below, the Rust pages are not written by
hand. `sphinx-rustdocgen` reads each crate listed under
`[tool.yardang.sphinx-rust]` and writes a page per module into the configured
`doc-dir`, so the only thing to author is a toctree pointing at the result:

```{toctree}
:hidden:
:maxdepth: 2

/api/crates/calculator/index
```

### Document Individual Items

Or document specific structs, enums, and functions:

```{eval-rst}
.. rust:struct:: calculator::Calculator

```

```{eval-rst}
.. rust:struct:: calculator::ScientificCalculator

```

```{eval-rst}
.. rust:enum:: calculator::Operation

```

```{eval-rst}
.. rust:enum:: calculator::CalculatorError

/api/calculator/lib
```

## JavaScript Example
Expand Down
90 changes: 47 additions & 43 deletions docs/src/configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -705,44 +705,68 @@ Then in your documentation files, you can use breathe directives:

## Sphinx-Rust Integration

Yardang provides integration with [sphinx-rust](https://sphinx-rust.readthedocs.io/) for documenting Rust code. To use this feature, install yardang with the sphinx-rust extra:
Yardang provides integration with [sphinxcontrib-rust](https://gitlab.com/munir0b0t/sphinxcontrib-rust) for documenting Rust code. To use this feature, install yardang with the rust extra:

```bash
pip install yardang[sphinx-rust]
pip install yardang[rust]
```

All sphinx-rust configuration is under `[tool.yardang.sphinx-rust]`.
This extra is GPL-3.0 licensed, unlike yardang itself, which is Apache-2.0. It also builds a `sphinx-rustdocgen` helper binary on install, so a Rust toolchain must be available.

All configuration is under `[tool.yardang.sphinx-rust]`.

### `crates`

A list of paths to Rust crates to document.
A mapping of crate name to crate directory. Every crate listed here is scanned and documented.

```toml
[tool.yardang.sphinx-rust]
crates = [
"path/to/crate1",
"path/to/crate2",
]
crates = { crate1 = "path/to/crate1", crate2 = "path/to/crate2" }
```

### `doc-dir`

Where the generated pages are written, relative to the documentation root. Defaults to `"api"`, producing `api/<crate>/lib.rst` for each crate.

```toml
[tool.yardang.sphinx-rust]
doc-dir = "api"
```

### `doc-formats`
### `rustdoc-fmt`

A dictionary mapping crate names to their docstring format. Valid values are `"restructuredtext"` (default) or `"myst-nb"` (for markdown docstrings).
The markup used inside Rust doc comments, either `"rst"` (default) or `"md"`. Accepts a single value for all crates, or a per-crate mapping.

```toml
[tool.yardang.sphinx-rust]
doc-formats = { mycrate = "myst-nb" }
rustdoc-fmt = { mycrate = "md" }
```

**Note:** When using `myst_nb` as your Sphinx parser (which yardang uses by default), use `"myst-nb"` instead of `"markdown"` for markdown docstrings.
### `visibility`

### `viewcode`
The minimum item visibility to document. Defaults to `"pub"`; use `"crate"` or `"pvt"` to include less visible items.

Enable links to the source code for documented items. Defaults to `true`.
```toml
[tool.yardang.sphinx-rust]
visibility = "pub"
```

### `strip-src`

Strip the `src` directory from generated paths. Defaults to `true`.

```toml
[tool.yardang.sphinx-rust]
viewcode = true
strip-src = true
```

### `generate-mode`

When to regenerate pages: `"changed"` (default), `"always"`, or `"skip"`.

```toml
[tool.yardang.sphinx-rust]
generate-mode = "changed"
```

### Complete Example
Expand All @@ -757,41 +781,21 @@ pages = ["docs/api.md", "docs/examples.md"]
use-autoapi = false

[tool.yardang.sphinx-rust]
crates = [
"crates/mylib",
"crates/mylib-utils",
]
doc-formats = { mylib = "myst-nb", "mylib-utils" = "restructuredtext" }
viewcode = true
crates = { mylib = "crates/mylib", mylib-utils = "crates/mylib-utils" }
doc-dir = "api"
rustdoc-fmt = { mylib = "md" }
```

Then in your documentation files, you can use sphinx-rust directives:
The pages are generated for you, so your documentation files only need a toctree entry pointing at them:

````markdown
# API Reference

## Document a Crate

\`\`\`{eval-rst}
.. rust:crate:: mylib

\`\`\`

## Document Individual Items

\`\`\`{eval-rst}
.. rust:struct:: mylib::MyStruct

\`\`\`

\`\`\`{eval-rst}
.. rust:enum:: mylib::MyEnum

\`\`\`

\`\`\`{eval-rst}
.. rust:function:: mylib::my_function
\`\`\`{toctree}
:maxdepth: 2

/api/mylib/lib
/api/mylib-utils/lib
\`\`\`
````

Expand Down
10 changes: 4 additions & 6 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ breathe = [
"breathe>=4.35.0",
]
rust = [
"sphinx-rust",
"sphinxcontrib-rust",
]
js = [
"sphinx-js>=5.0.0",
Expand Down Expand Up @@ -82,7 +82,7 @@ develop = [
"wheel",
# Extensions
"breathe>=4.35.0",
"sphinx-rust",
"sphinxcontrib-rust",
"sphinx-js>=5.0.0",
# Themes
"shibuya",
Expand Down Expand Up @@ -206,10 +206,8 @@ projects = { calculator = "examples/cpp/xml" }
default-project = "calculator"

[tool.yardang.sphinx-rust]
crates = [
"examples/rust",
]
doc-formats = { calculator = "myst-nb" }
crates = { calculator = "examples/rust" }
doc-dir = "api"

[tool.yardang.sphinx-js]
js-language = "javascript"
Expand Down
29 changes: 17 additions & 12 deletions yardang/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -345,18 +345,18 @@ def customize(args):
"doxygendefine",
"doxygenunion",
"doxygenvariable",
# sphinx-rust directives
# sphinxcontrib-rust directives
"rust:crate",
"rust:module",
"rust:struct",
"rust:enum",
"rust:function",
"rust:method",
"rust:executable",
"rust:trait",
"rust:impl",
"rust:type",
"rust:const",
"rust:static",
"rust:use",
"rust:variable",
"rust:macro",
# sphinx-js directives
"js:autofunction",
Expand Down Expand Up @@ -440,27 +440,32 @@ def customize(args):
name: str(Path(path).resolve()) if not Path(path).is_absolute() else path for name, path in breathe_args["breathe_projects"].items()
}

# Load sphinx-rust configuration from tool.yardang.sphinx-rust
# Load sphinxcontrib-rust configuration from tool.yardang.sphinx-rust
rust_config_base = f"{config_base}.sphinx-rust"
rust_args = {}
for config_option, default in {
# sphinx-rust
"rust_crates": [],
"rust_doc_formats": {},
"rust_viewcode": True,
# sphinxcontrib-rust
"rust_crates": {},
"rust_doc_dir": "api",
"rust_rustdoc_fmt": "rst",
"rust_visibility": "pub",
"rust_strip_src": True,
"rust_generate_mode": "changed",
}.items():
# config keys in toml use hyphens, not underscores, and no rust_ prefix
toml_key = config_option.replace("rust_", "").replace("_", "-")
rust_args[config_option] = get_config(section=toml_key, base=rust_config_base)
if rust_args[config_option] is None:
rust_args[config_option] = default

# Determine if sphinx-rust should be used
# Determine if sphinxcontrib-rust should be used
use_sphinx_rust = bool(rust_args["rust_crates"])

# Convert relative paths in rust_crates to absolute paths
# Crates are a name -> directory mapping; the generator needs absolute paths
if rust_args["rust_crates"]:
rust_args["rust_crates"] = [str(Path(path).resolve()) if not Path(path).is_absolute() else path for path in rust_args["rust_crates"]]
rust_args["rust_crates"] = {
name: str(Path(path).resolve()) if not Path(path).is_absolute() else path for name, path in rust_args["rust_crates"].items()
}

# Load sphinx-js configuration from tool.yardang.sphinx-js
js_config_base = f"{config_base}.sphinx-js"
Expand Down
21 changes: 16 additions & 5 deletions yardang/conf.py.j2
Original file line number Diff line number Diff line change
Expand Up @@ -92,9 +92,9 @@ if use_search:
if use_breathe:
extensions.append("breathe")

# Add sphinx-rust extension if configured
# Add sphinxcontrib-rust extension if configured
if use_sphinx_rust:
extensions.append("sphinx_rust")
extensions.append("sphinxcontrib_rust")

# Add sphinx-js extension if configured
if use_sphinx_js:
Expand Down Expand Up @@ -223,11 +223,22 @@ if use_breathe:
breathe_order_parameters_first = {{breathe_order_parameters_first}}
breathe_separate_member_pages = {{breathe_separate_member_pages}}

# sphinx-rust configuration
# sphinxcontrib-rust configuration
if use_sphinx_rust:
rust_crates = {{rust_crates}}
rust_doc_formats = {{rust_doc_formats}}
rust_viewcode = {{rust_viewcode}}
rust_doc_dir = "{{rust_doc_dir}}"
{% if rust_rustdoc_fmt is string %}
rust_rustdoc_fmt = "{{rust_rustdoc_fmt}}"
{% else %}
rust_rustdoc_fmt = {{rust_rustdoc_fmt}}
{% endif %}
{% if rust_visibility is string %}
rust_visibility = "{{rust_visibility}}"
{% else %}
rust_visibility = {{rust_visibility}}
{% endif %}
rust_strip_src = {{rust_strip_src}}
rust_generate_mode = "{{rust_generate_mode}}"

# sphinx-js configuration
if use_sphinx_js:
Expand Down
Loading