Enum variant with cfg(test) cant be found in a test written in a different crate

I'm not sure if this is a bug or intended behaviour.

in A/src/main.rs

#[cfg(test)]
mod test {
    use B::Foo;

    #[test]
    fn check() {
        let a = Foo::A;
        let b = Foo::B("haha".to_string());

        println!("{a:?}, {b:?}")
    }
}

in B/src/lib.rs

#[derive(Debug)]
pub enum Foo {
    A,
    #[cfg(test)]
    B(String),
}

cargo test exits with

error[E0599]: no variant or associated item named `B` found for enum `Foo` in the current scope
 --> src/main.rs:9:22
  |
9 |         let b = Foo::B("haha".to_string());
  |                      ^
  |                      |
  |                      variant or associated item not found in `Foo`
  |                      help: there is a variant with a similar name: `A`

It's not a bug. #[cfg(test)] is only set for the crate being tested. It's not set for any other crate.

If you need an item for testing another crate, you'll have to make it public.

I suggest you make a lib. feature for “B” named "test", "testing" or "test_util". It will be disabled by default and people using your library won't see these “test” enum. variants. But they will be able to opt into using them by enabling your "testing" feature.

So when testing “B” from “A” you'll just enable “testing” feature. Like B = { version="0.1.0", features=["testing"] }.

1 Like

Note however that this feature should never, ever, be expected to become necessary for others (i.e. it should not unlock any functionality for anyone but yourself). See the previous discussion in A possible edge case for semver.

1 Like