How do I check/clippy everything?

Hey folks,

I don't know if I'm over-thinking this but it's not clear to me so figured I'd ask. I'm working on a workspace project with a pre-commit hook I'd like to have run clippy and cargo fmt. It has various tests and examples. I sometimes find that clippy misses some things, and I think I may not be running it on all workspace components. My questions:

  1. What does cargo clippy vs. cargo clippy --all or --workspace do? Is --all or --workspace implied, or does a bare cargo clippy invocation do something different?
  2. Probably answered above, and if so no need to belabor, but does bare cargo clippy or --all imply any or all of --bins, --tests, and --examples`?
  3. Is it the same across all commands? In this case I'm running cargo fmt and cargo clippy, so I want to make sure all crates in the workspace plus their binaries/tests/examples are formatted and linted.
  4. How do features fit into this? I can't necessarily always compile all my features everywhere, but I'm guessing cargo fmt doesn't require compiling so could technically format a feature not compilable on a given platform? What about clippy? Can it do basic code analysis without compiling, or does it need to compile a feature to lint it? Wondering if my invocations need to be --workspace --all-features or if --all-features is implied in some/both of these commands.

Thanks!

Yes, in a workspace, cargo clippy does the same as cargo clippy --all or cargo clippy --workspace. Note that --all is deprecated in favour of --workspace.

Edit: cargo clippy only selects the same packages as cargo clippy --workspace depending on how the workspace is configured (for me it usually is; sorry for the confusion). From the docs:

The default members of a workspace can be set explicitly with the workspace.default-members key in the root manifest. If this is not set, a virtual workspace will include all workspace members (equivalent to passing --workspace), and a non-virtual workspace will include only the root crate itself.


No, target selection is not influenced by --workspace. cargo clippy by default lints binary targets and the lib target, if present. You can use --all-targets to also lint tests and examples and benchmarks.


I believe yes. cargo fmt, same as cargo clippy, has the same workspace and target selection defaults as cargo check.

Edit: I believe cargo fmt does format every target. I can't find any options to run it only for specific targets. It doesn't format unlinked *.rs files though.


Yes, features are not distinguished by cargo fmt. Clippy does compile your workspace packages (it wraps cargo check). It does enable the default features if you don't define them as arguments or pass --all-features.


All this being said, this is the cargo clippy command I use in most of my personal projects' CI:

cargo clippy --all-features --all-targets -- -D warnings -D clippy::pedantic

According to the cargo --help for clippy/check:

 --all               Alias for --workspace (deprecated)

It doesn't say anything about being implied.

The cargo fmt help has a different definition for -all

      --all
          Format all packages, and also their local path-based dependencies

You almost certainly don't check/clippy everything; although it's a noble goal. Each use of #[cfg] in your code is an area that won't be checked unless it's enabled. For example,

#[cfg(not(unix))]
pub struct Foo;
#[cfg(not(unix))]
impl Foo {
    fn bar() {
        jibberish
    }
}

Unless you actually check/clippy the code on a non-unix platform, that code—which isn't even valid Rust (although it is valid syntax)—will not be checked. Even for a given target platform, features alone have an exponential impact on what you need to test since the cardinality of the power set of a set A is 2^|A| where |A| is the cardinality of A[1]. It's actually quite common to find certain combinations of features that will cause a compilation failure for crates on crates.io very popular crates not withstanding even when one excludes a compilation error from compile_error.

Fortunately while crates likes winapi exist with 399 features, a vast majority of crates don't exceed a dozen making it feasible for a large proportion of crates to test each combination of features (even if you don't remove semantically equivalent sets). It is not common to test all combinations though; while I do—I've written a CI tool that generates the semantically distinct sets of features before running cargo clippy --all-targets and cargo t on each set for both stable and the MSRV toolchain (if it's defined)—if I didn't, I'd just check --all-features and possibly the default feature as well (or no features if there is no default feature).


  1. Technically since it's not uncommon to have features that depend on other features, this is an upper bound; however even if you only test semantically distinct sets of features, it's still an exponential function. ↩︎

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.