Rust Tooling and Code Quality
cargo metadata
The cargo metadata command outputs a machine-readable JSON document describing the workspace structure, package manifests, compilation targets, resolved dependency graph, and active features. IDEs (such as rust-analyzer), build wrappers, security scanners, and custom cargo xtask tools invoke cargo metadata --format-version 1 instead of parsing Cargo.toml files by hand.
Cargo.toml + Cargo.lock + .cargo/config.toml
|
v `cargo metadata --format-version 1 --no-deps`
[ JSON Document on stdout ]
├── "packages": [ { "name", "version", "targets", "features", ... } ]
├── "workspace_members": [ ... ]
├── "workspace_root": "/path/to/workspace"
├── "target_directory": "/path/to/workspace/target"
└── "resolve": { "nodes": [ ... ], "root": ... }
Key Flags for cargo metadata
Always pass --format-version 1 when calling cargo metadata so Cargo guarantees a stable JSON schema:
| Command | Behavior |
|---|---|
cargo metadata --format-version 1 |
Outputs full JSON metadata including all transitive dependencies and resolved feature nodes (downloads missing registry metadata if needed). |
cargo metadata --format-version 1 --no-deps |
Outputs metadata only for workspace member packages without resolving external dependencies (instantaneous and offline!). |
cargo metadata --format-version 1 --locked |
Ensures Cargo.lock is up to date while generating resolved dependency metadata. |
Top-Level Fields in the JSON Schema
{
"packages": [
{
"name": "my_service",
"version": "0.1.0",
"id": "path+file:///Users/dev/my_service#0.1.0",
"edition": "2024",
"rust_version": "1.85",
"manifest_path": "/Users/dev/my_service/Cargo.toml",
"targets": [
{
"kind": ["bin"],
"crate_types": ["bin"],
"name": "my_service",
"src_path": "/Users/dev/my_service/src/main.rs",
"edition": "2024"
}
],
"features": {
"default": ["std"],
"std": []
}
}
],
"workspace_members": [
"path+file:///Users/dev/my_service#0.1.0"
],
"workspace_root": "/Users/dev/my_service",
"target_directory": "/Users/dev/my_service/target",
"version": 1
}
Invoking cargo metadata from a Rust Tool
In cargo xtask or custom CLI tools, you can run cargo metadata --format-version 1 --no-deps via std::process::Command (or via the cargo_metadata crate when serde is available) to discover workspace roots and member paths:
use std::process::Command;
fn extract_json_string_field<'a>(json: &'a str, key: &str) -> Option<&'a str> {
let pattern = format!("\"{key}\":\"");
let start = json.find(&pattern)? + pattern.len();
let rest = &json[start..];
let end = rest.find('"')?;
Some(&rest[..end])
}
fn main() {
let sample_json = r#"{"workspace_root":"/Users/dev/workspace","target_directory":"/Users/dev/workspace/target","version":1}"#;
let root = extract_json_string_field(sample_json, "workspace_root").unwrap();
let target = extract_json_string_field(sample_json, "target_directory").unwrap();
// Also verify `cargo --version` is callable via Command
let cargo_ok = Command::new("cargo")
.arg("--version")
.output()
.map(|o| o.status.success())
.unwrap_or(false);
println!("Workspace root: {root}");
println!("Target directory: {target}");
println!("Cargo available: {cargo_ok}");
}
Workspace root: /Users/dev/workspace
Target directory: /Users/dev/workspace/target
Cargo available: true