Search code examples
rustrustdoc

Break long table rows into multiple lines in documentation


I want to document my crate and include a table in the documentation:

//! Demonstrating MarkDown tables.
//!
//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀 | I can't think of any more "funny" things | oopsie |
//!

Rendering this with cargo doc results in:

correct table

This is what I want. However, you might have noticed that the one source code line is very long. In fact, over 100 characters long. Like many Rust projects, I want to keep all my lines under 100 characters long. So I tried to break the line somehow.

All of these versions:

//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀 
//! I can't think of any more "funny" things | oopsie |

//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀 |
//! I can't think of any more "funny" things | oopsie |

//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀
//! | I can't think of any more "funny" things | oopsie |

//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀 |
//! | I can't think of any more "funny" things | oopsie |

//! | Foo | Bar | Baz | Qux |
//! | --- | --- | --- | --- |
//! | Hail the turbofish `::<>` | Ferris for president 🦀 \
//! I can't think of any more "funny" things | oopsie |

Results in:

enter image description here

What options do I have to include long table rows in my documentation without violating the line length limit?


Solution

  • HTML

    As already answered by Francis, you have to use HTML if you'd like to keep short lines. rustdoc utilizes pulldown-cmark and there's no support for what you want.

    Include external documentation

    nightly & doc

    Tracking issue: rfc 1990 - add external doc attribute to rustc. In case of nightly toolchain, you can enable external_doc feature and include external Markdown files with #[doc(include = "../some/path")].

    One thing to note - no matter in what module you will use #[doc(include = "...")], the path is always relative to the crate root (lib.rs, main.rs, ...).

    Example:

    .
    |____Cargo.toml
    |____Cargo.lock
    |____doc
    | |____foo-bar-bar.md
    |____src
    | |____main-hallo.md
    | |____foo
    | | |____mod.rs
    | | |____bar.rs
    | |____main.rs
    

    src/main.rs:

    #![feature(external_doc)]
    
    pub mod foo;
    
    #[doc(include = "main-hallo.md")]
    pub fn hallo() {}
    
    fn main() {}
    

    src/foo/bar.rs:

    #[doc(include = "../doc/foo-bar-bar.md")]
    pub struct Bar;
    

    You can keep separate Markdown documentation in the src/ folder, you can have it in a separate folder like doc/, etc. But the path is always relative to the crate root.

    nightly & rdoc

    There's also rdoc compiler plugin (requires nightly), which basically does the same thing. How to enable & use it is described in the project README.md.

    stable

    For stable, I'd do the following:

    • documentation in separate Markdown files,
    • custom build.rs which will scan for .md files and outputs them as .rs files (same content, just prepend every line with /// or //!),
      • put them in the std::env::var("OUT_DIR") folder,
    • include them in your source code,
      • via include!(concat!(env!("OUT_DIR"), "/main-hallo-md.rs"));.

    rustfmt & nightly

    There's comment_width option (defaults to 80) & wrap_comments option (defaults to false). This helps you to keep comments up to some width. But I tried it with the long Markdown table line and it wrapped it -> broken table. Don't use it.