Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rustdoc --test should be able to expand exported macros defined in the same crate #16893

Closed
japaric opened this issue Aug 31, 2014 · 4 comments
Closed
Labels
T-rustdoc Relevant to the rustdoc team, which will review and decide on the PR/issue.

Comments

@japaric
Copy link
Member

japaric commented Aug 31, 2014

I have lots of doctests/examples like this one in my library:

#![feature(macro_rules)]

#[macro_export]
/// Construct a `Mat` containing the arguments
macro_rules! mat {
    () => { unimplemented!() };
}

pub struct Mat;

impl Mat {
    /// Constructs a matrix filled with zeros
    ///
    /// # Example
    ///
    /// ```
    /// assert_eq!(Mat::zeros((2, 2)), mat![0, 0; 0, 0])
    /// ```
    pub fn zeros(size: (uint, uint)) -> Mat {
        unimplemented!();
    }
}

But rustdoc is not able to expand the mat! macro, which is defined and exported in the same crate:

$ rustdoc --test lib.rs
running 1 test
test zeros_0 ... FAILED

failures:

---- zeros_0 stdout ----
        <anon>:5:36: 5:39 error: macro undefined: 'mat!'
        <anon>:5     assert_eq!(Mat::zeros((2, 2)), mat![0, 0; 0, 0])
                                                    ^~~
        error: aborting due to previous error
        task 'zeros_0' failed at 'Box<Any>', /var/tmp/paludis/build/dev-lang-rust-scm/work/rust-scm/src/libsyntax/ast_util.rs:784



failures:
    zeros_0

test result: FAILED. 0 passed; 1 failed; 0 ignored; 0 measured

task '<unnamed>' failed at 'Some tests failed', /var/tmp/paludis/build/dev-lang-rust-scm/work/rust-scm/src/libtest/lib.rs:242

It'd be great if this worked. (Meanwhile, I'll mark my doctests as ignored)

@huonw
Copy link
Member

huonw commented Aug 31, 2014

This is just because rustdoc inserts runs each test as it's own binary, by inserting extern crate $your_crate; (if extern crate doesn't occur in the example) and wrapping the contents in fn main() { ... } (if fn main doesn't occur in it).

Specifically the crate is being loaded without loading macros: there is no #[phase(plugin)]. While this is all feature gated I'm inclined to leave it this way, but maybe the requirement for #[feature(macro_rules)] on the main crate is enough to opt-in to rustdoc inserting #[phase(plugin)] too.

In any case, you can work around this by manually loading the crate in the example:

```rust
#![feature(phase)]

#[phase(plugin, link)] extern crate foo;
fn main() {
    // example here
}
```

Leading # allow you to control the output precisely, e.g.

```rust
# #![feature(phase)] #[phase(plugin, link)] extern crate foo;
# fn main() {
assert_eq!(Mat::zeros((2,2)), mat![0, 0; 0, 0])
# }
```

will display the same way as your example there.

@japaric
Copy link
Member Author

japaric commented Aug 31, 2014

@huonw Thanks a lot for the workaround! I didn't know about the leading # in doc comments.

Although, it's quite a bit of boilerplate, having the doctests enabled is totally worth it. 👍

@kmcallister
Copy link
Contributor

Maybe the simple fix is a new rustdoc feature

```rust,macro_test

which includes a #[macro_use] extern crate foo; outside of the implicit fn main().

@alexcrichton
Copy link
Member

The workaround was documented in #23618, so I'm going to close this now.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
T-rustdoc Relevant to the rustdoc team, which will review and decide on the PR/issue.
Projects
None yet
Development

No branches or pull requests

4 participants