Cannot call a parent package from within test module


#1

Dear all,

I have a crate like this:

src/
├── ast
│   └── mod.rs
├── compiler
│   ├── cgenerator.rs
│   ├── constraints.rs
│   ├── declarations.rs
│   ├── evaluate.rs
│   ├── expression.rs
│   ├── lipid_database.rs
│   ├── ltl_generator.rs
│   ├── mod.rs
│   ├── options.rs
│   ├── report.rs
│   └── utils.rs
├── grammar-bnf.txt
├── grammar.lalrpop
├── grammar.rs
├── grammar.rs.bk
├── lib.rs
├── main.rs
├── parser.rs
├── tests.rs
└── tok
    ├── lexer.rs
    ├── lexer.rs.bk
    └── mod.rs

In ltl_generator.rs I have a test module in which I like to call a macro I defined in utils.rs:

#[cfg(test)]
mod test {
   #[test]
   ltl_test() {
      #[macro_use] use compiler::utils;
      ...
   }
}

The macro is included in compiler/mod.rs:

   #[macro_use] pub mod utils;

However, cargo test tells me:

$ cargo test compiler::ltl_generator::test::ltl_generation -- --nocapture
   Compiling mfql v0.1.0 (file:///home/herzog/Lipotype/ltx2/backend/mfql)
error: cannot find macro `candidate!` in this scope
  --> compiler/ltl_generator.rs:86:25
   |
86 |         let candidate = candidate!(ast::DeclKind::Intact,
   |                         ^^^^^^^^^
   |
   = help: have you added the `#[macro_use]` on the module/import?

error: aborting due to previous error(s)

error: Could not compile `mfql`.

I don’t know what is wrong here. Any help is appreciated.

Ronny


#2

This may be an ordering problem. Unlike everything else in Rust, macro_rules macros must be defined before you use them, so typically when you get an error saying “cannot find macro foo! in this scope” it’ll be because (from the crate’s perspective) you’re trying to use a macro before declaring it.

Here’s a more concrete example of what I think is happening:

pub mod baz;

macro_rules! bar {
    () => ("Hello World")
}

fn main() {
    println!("{}", baz::foo());
}

Where my baz.rs contains:

pub fn foo() -> &'static str {
    bar!()
}

Compiling that (playground link) then results in an error similar to what you got.

rustc 1.18.0 (03fc9d622 2017-06-06)
error: cannot find macro `bar!` in this scope
 --> <anon>:3:9
  |
3 |         bar!()
  |         ^^^
  |
  = help: have you added the `#[macro_use]` on the module/import?

error: aborting due to previous error

The fix is usually to rearrange the mod statements in your root lib.rs so that any modules which export macros are above the things which use them.

You may want to have a look at the Little book of Rust Macros for more info.


#3

Thanks for the hint. This was exactly the problem.