How can I enable rust's cargo features to compile code conditionally based on operating system?

We have tests that are broken on macOS for some reason and they are to be investigated when the time is right as they're in the backlog. Currently, they're disabled with

#[cfg(not(target_os = "macos"))]

However, this has the horrible side effect that enabling all these tests will require doing it one by one, which is very inconvenient and makes testing the side effects of other changes much harder.

Please note that using the #[ignore] modifier for these tests isn't really an option because there are many other ignored tests for other reasons (let's say for the right reasons, such as they're heavy and shouldn't be run regularly).

In C++, I would just wrap them in an #ifdef macro and just comment/uncomment a line in cmake to control whether these tests will be run.

In Rust, as far as I understand, the feature feature is the right way to do this. I'm very close to getting this to work, so now above every one of these tests I have

#[cfg(not(feature = "no-mac-tcp-tests"))]

and in Cargo.toml of the relevant crate:

[features]
no-mac-tcp-tests = []

This has the intended side-effect, except that I can't tell cargo to, by default, disable this for mac. I tried

[target.'cfg(target_os = "macos")'.features]
no-mac-tcp-tests = []

but that doesn't work. I know that doesn't work as intended because changing macos to windows doesn't really do anything on my mac machine.

How can I achieve my goal, namely, disable a bunch of tests based on a flag in the crate's Cargo.toml depending on the OS?

You can use the default feature.

[target.'cfg(target_os = "macos")'.features]
default  = []
no-mac-tcp-tests = []

[target.'cfg(not(target_os = "macos"))'.features]
default  = ["no- mac-tcp-test"]
no-mac-tcp-tests = []

This doesn't seem to work. Moving that quoted feature name from the second group to the first group doesn't change the state of the test, being enabled or disabled.

My bad. I forgot to actually specify the no-mac-tcp-tests feature.
The thing with cargo features is that they are disabled if they are left as is. So if you want to enable them, you have to make it transitively enabled via the default feature. You can make use of that to do what you are aiming for.

Thank you for trying to help. I really appreciate it.

I'm trying to understand what you mean, but your edited code doesn't work too (by testing what happens when we move the feature "string" from one group to another, as I find it doesn't change anything. You have two typos there that I fixed (extra-space + missing letter 's' at the end), but that still didn't fix the issue.

I fixed the issue by putting this above every relevant test

#[cfg(any(not(target_os = "macos"), feature = "mac-force-tcp-tests"))]

and in Cargo.toml

[features]
default = ["mac-force-tcp-tests"]
mac-force-p2p-tcp-tests = []

This gave me full central control from the cargo file choosing to comment the features' 3 lines.

1 Like