cargo-docs-md 0.2.4

Generate per-module markdown documentation from rustdoc JSON output
Documentation
# cargo-docs-md

Turn rustdoc JSON into markdown you can actually navigate. Your code and all your dependencies, documented and searchable, navigable with reference links in one place.

The [`generated_docs/`](generated_docs/) folder in this repo has 90 crates, 1,286 markdown files, and 24,000+ searchable items generated from this tool's own dependency tree. Checkout the added docs and source code directly in repo to see how well it currently works (or not!).

## Current Features

**Clickable everything.** Each file has breadcrumb navigation at the top. References to types, traits, and functions link to their definitions — even across crates. For example, `regex_automata` docs link directly to `regex_syntax::hir::Hir`.

```markdown
*[cargo_docs_md](../../index.md) / [generator](../index.md) / [context](index.md)*
```

**Source locations.** Every item shows where it's defined. Click through to the exact file and line.

For your own crate:

```markdown
*Defined in `src/generator/context.rs:135-168`*
```

For dependencies (with `collect-sources`):

```markdown
*Defined in [`compact_str-0.9.0/src/lib.rs:128`](../../.source_1765521767/compact_str-0.9.0/src/lib.rs#L128)*
```

**Full method documentation.** Methods include their complete documentation with examples:

```markdown
- `fn push(&mut self, ch: char)`

  Appends the given char to the end of this CompactString.

  # Examples
  ...
```

**Search index.** A `search_index.json` with every documented item — name, path, kind, and file location.

## Installation

Requires Rust nightly (rustdoc JSON is unstable):

```bash
rustup toolchain install nightly
cargo install cargo-docs-md
```

## Usage

```bash

# You need to run an extra command to collect your dependencies source code and 
# make a local copy directly into your project. It renames all Cargo.toml into Crate.toml 
# so that rust-analyzer ignores them by default.

cargo docs-md collect-sources
cargo docs-md docs
```

That's it. Builds rustdoc JSON and generates markdown in one step.

```bash
cargo docs-md docs --primary-crate my_crate   # prioritize your crate for link resolution
cargo docs-md docs --exclude-private          # public items only
cargo docs-md docs --clean                    # full rebuild (cargo clean first)
```

### Source file collection

To make source links work for dependencies, collect their source files first:

```bash
cargo docs-md collect-sources   # copies sources to .source_{timestamp}/
cargo docs-md docs              # auto-detects and links to them
```

This snapshots dependency sources at their exact versions, so links stay valid even after updates.

**Source collection options:**

| Flag | Effect |
|------|--------|
| `--minimal-sources` | Only copy `src/` and `Cargo.toml` (smaller, may miss some files) |
| `--no-gitignore` | Don't add `.source_*` to `.gitignore` |
| `--include-dev` | Include dev-dependencies |
| `--dry-run` | Show what would be collected without copying |

By default, the entire crate directory is copied to ensure all source files are available (including `build.rs`, modules outside `src/`, etc.).

### Maximum detail output

For the most comprehensive documentation with all available information:

```bash
cargo docs-md collect-sources
cargo docs-md docs \
  --include-blanket-impls \
  --source-locations \
  --full-method-docs
```

This enables:

- **Blanket impls** — Shows `From`, `Into`, `Any`, `Borrow`, etc. implementations
- **Source locations** — Links to exact file and line for every item
- **Full method docs** — Complete method documentation with examples (not just summaries)

### More options

**Add more detail:**

| Flag | Effect |
|------|--------|
| `--include-blanket-impls` | Include `From`, `Into`, `Any`, `Borrow`, etc. |
| `--source-locations` | Show source file locations with clickable links |
| `--full-method-docs` | Include full method docs instead of first-paragraph summaries |

**Reduce output:**

| Flag | Effect |
|------|--------|
| `--exclude-private` | Public items only |
| `--no-mdbook` | Skip `SUMMARY.md` generation (multi-crate mode) |
| `--no-search-index` | Skip `search_index.json` (multi-crate mode) |
| `--no-quick-reference` | Skip Quick Reference table |
| `--no-group-impls` | Don't group impls by category |
| `--hide-trivial-derives` | Collapse common derive traits (Debug, Clone, etc.) |
| `--no-method-anchors` | Skip method deep-link anchors |

Note: In multi-crate mode (`docs` subcommand or `--dir`), mdBook and search index are generated by default. Use `--no-mdbook` and `--no-search-index` to disable them.

**Other options:**

| Flag | Effect |
|------|--------|
| `--format flat` | All markdown files in one directory |
| `--toc-threshold N` | Minimum items for TOC generation (default: 10) |
| `--primary-crate NAME` | Prioritize this crate for link resolution |

For manual control, generate rustdoc JSON yourself:

```bash
RUSTDOCFLAGS='-Z unstable-options --output-format json' cargo +nightly doc
cargo docs-md --dir target/doc/ -o docs/
```

## How it works

Reads rustdoc JSON and walks the module tree. For each module, collects all items, renders their docs, and resolves cross-reference links using rustdoc's link map.

Multi-crate workspaces get a unified link registry that tracks items across all crates. When the same name exists in multiple places, it resolves by checking: local crate first, then primary crate (if set), then any module match, then first available.

## Known limitations

- **No standard library links.** References to `Vec`, `String`, `Drop`, etc. can't link to std docs since they're not in the generated output. They may incorrectly resolve to a same-named item in your dependencies.

- **Nightly only.** Rustdoc JSON is unstable and requires the nightly toolchain. The format can change between Rust versions.

- **Ambiguous names.** When multiple crates export the same name, the resolver picks one based on priority rules. This is usually correct, but occasionally produces unexpected links.

- **Private item links.** By default, private items are documented. If you later regenerate with `--exclude-private`, links pointing to those items will break.

## Development

```bash
just help         # all commands
just test         # run tests
just lint         # clippy (pedantic + nursery)
just docs         # full rebuild
```

## License

MIT