How to reference the test of another crate in the current crate

I expect to reference A's test tool code in B, but that doesn't seem to work, and the test tag won't be passed to A crate when cargo test is performed.

crate a:

#[cfg!(test)]
pub mod test_utils {
    use std::path::PathBuf;

    pub fn test_dir() -> PathBuf {
        todo!()
    }
}

crate b

#[test]
fn test_xxx()  {
    let dir = a::test_utils::test_dir();
    todo!()
}

So I started using for-test feature instead of the test tag, but this has another problem. Suppose A implements the for-test feature, B can make it take effect in dev-dependencies, but A cannot make the for-test feature take effect in tests.
crate B can use [dev-dependencies]

[dev-dependencies]
A   = { workspace = true, features = ["for-test"] }

crate A can't

Cargo.toml
[features]
for-test  = []

src
   test_util.rs // cfg  for-test
tests
   xxx_test.rs // Unable to use test_util

Would it be possible for you to abstract the test utility functionality you share across workspace members into its own workspace member? Like create a new crate C, put test_dir in it and add C as dev-dependency to A and B?

My usage scenario does not allow abstracting a C, because it involves the code of B. In actual code, I've put what I can abstract into C (test-utils).

I think I found a workaround for this:

(found the link in this SO answer: unit testing - Is it possible to enable a rust feature only in test? - Stack Overflow)

The workaround requires you to add the following to the Cargo.toml of your A crate:

[dev-dependencies]
A = { path = ".", features = ["for-test"] }

which should allow you to simply run cargo test in A where A has the for-test feature enabled.


Alternatively you can run cargo test --features for-test in A to enable the desired optional feature during testing.

Yes, but I don't want to do it through --features for-test, because I think it's weird, and I'd prefer to do it through cargo test.

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.