Skip to content

Commit 2c1158d

Browse files
committed
cargo-rail: update the readme; fix the strict_version_compat options; clarify the msrv design in the readme
1 parent 6fd5bf6 commit 2c1158d

File tree

23 files changed

+339
-187
lines changed

23 files changed

+339
-187
lines changed

README.md

Lines changed: 60 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,16 @@
11
# cargo-rail
22

3+
> **⚠️ WORK IN PROGRESS - NOT CANONICAL ⚠️**
4+
>
5+
> This project is under active development. APIs, configuration options, and behaviors may change without notice.
6+
37
**Monorepo orchestration for Rust workspaces.**
48

59
[![Crates.io](https://img.shields.io/crates/v/cargo-rail.svg)](https://crates.io/crates/cargo-rail)
610
[![License: MIT](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)
711
[![Rust 1.91+](https://img.shields.io/badge/rust-1.91%2B-orange.svg)](https://www.rust-lang.org)
812

9-
[Commands](docs/commands.md) · [Config](docs/config.md) · [Recipes](docs/recipes.md) · [Crates.io](https://crates.io/crates/cargo-rail)
13+
[Commands](docs/commands.md) | [Config](docs/config.md) | [Recipes](docs/recipes.md) | [Crates.io](https://crates.io/crates/cargo-rail)
1014

1115
```bash
1216
cargo install cargo-rail
@@ -16,48 +20,66 @@ cargo install cargo-rail
1620

1721
## What It Does
1822

19-
**Test only what changed** Graph-aware change detection. Auto-detects nextest. 70-90% CI reduction.
23+
**Test only what changed** - Graph-aware change detection. Auto-detects nextest.
2024

2125
```bash
2226
cargo rail test
2327
```
2428

25-
**Unify dependencies** Resolution-based `[workspace.dependencies]` without workspace-hack crates.
29+
**Unify dependencies** - Resolution-based `[workspace.dependencies]` management.
2630

2731
```bash
2832
cargo rail unify --check # Preview
2933
cargo rail unify # Apply
3034
```
3135

32-
**Split crates with history** Extract crates to standalone repos. Deterministic SHAs, git-notes mapping.
36+
**Split crates with history** - Extract crates to standalone repos with deterministic SHAs.
3337

3438
```bash
3539
cargo rail split run my-crate
3640
```
3741

38-
**Sync bidirectionally** Monorepo split repo. Changes from external repos create PR branches.
42+
**Sync bidirectionally** - Monorepo to split repo and back. External changes create PR branches.
3943

4044
```bash
4145
cargo rail sync my-crate
4246
```
4347

44-
**Release with ordering** Dependency-ordered publishing. Native changelog generation.
48+
**Release with ordering** - Dependency-ordered publishing with changelog generation.
4549

4650
```bash
47-
cargo rail release run --all --bump minor --check
51+
cargo rail release run --all --bump minor
4852
```
4953

5054
---
5155

52-
## Why cargo-rail
56+
## How It Works
5357

54-
**11 dependencies, ~100 resolved.** Compare: cargo-hakari pulls ~40 direct via guppy. release-plz pulls 600+ resolved.
58+
cargo-rail runs `cargo metadata --filter-platform` for each target triple in your workspace, then computes:
5559

56-
**Multi-target resolution.** Queries Cargo's actual resolver across all your target triples. Computes intersection of required features (not union).
60+
1. **Resolved versions** - What Cargo's resolver actually picked, not declared versions
61+
2. **Feature sets** - Intersection for workspace deps, union fallback for edge cases
62+
3. **MSRV floor** - Maximum `rust-version` from the entire resolved graph
63+
4. **Unused deps** - Declared but absent from resolution
64+
5. **Dead features** - Declared but never enabled anywhere
5765

58-
**System git.** Uses `git` binary directly. No libgit2/gitoxide. Deterministic SHAs. git-notes for rebase-safe commit mapping.
66+
One metadata pass per target. No additional cargo invocations. No workspace-hack crate.
5967

60-
**Lossless TOML.** Uses `toml_edit` to preserve comments and formatting.
68+
---
69+
70+
## The Unify Algorithm
71+
72+
**Versions**: Uses Cargo's resolved versions across all configured targets. Multiple major versions of the same dep trigger a warning and skip unification for that dep (configurable to force-bump to highest).
73+
74+
**Features**: Workspace deps carry the intersection (common features across all usages). Members declare local additions via `features = ["extra"]`. Target-specific features (`[target.'cfg(...)'.dependencies]`) stay in member manifests.
75+
76+
**MSRV**: Computes the maximum `rust-version` declared by any package in your resolved dependency graph. This is your buildable floor - the minimum Rust version that can compile your workspace. Written to `[workspace.package].rust-version`.
77+
78+
**Unused deps**: Compares declared dependencies against the resolved graph. If a dep isn't in the resolution for any configured target, it's unused. Conservative filters prevent false positives for optional deps, feature-gated deps, and unconfigured targets.
79+
80+
**Dead features**: Features declared but never enabled in the resolved graph. Only empty no-op features (`feature = []`) are pruned. Features that enable something are reported but preserved - they're user-facing API.
81+
82+
**Transitive pinning**: Optional. Detects transitive-only deps with fragmented features across targets and pins them in `[workspace.dependencies]`. Replaces workspace-hack crates without the lockstep maintenance.
6183

6284
---
6385

@@ -69,12 +91,11 @@ cargo rail release run --all --bump minor --check
6991
| `test` | Run tests for affected crates only |
7092
| `unify` | Unify deps to `[workspace.dependencies]` |
7193
| `split` | Extract crate to standalone repo with history |
72-
| `sync` | Bidirectional monoreposplit repo sync |
94+
| `sync` | Bidirectional monorepo/split repo sync |
7395
| `release` | Version bump, changelog, tag, publish |
7496
| `init` | Generate `rail.toml` |
7597
| `check` | Validate release readiness |
7698
| `clean` | Remove generated artifacts |
77-
| `config` | Validate configuration |
7899

79100
Run `cargo rail <command> --help` for details, or see [docs/commands.md](docs/commands.md).
80101

@@ -92,11 +113,12 @@ Searched in order: `rail.toml`, `.rail.toml`, `.cargo/rail.toml`, `.config/rail.
92113
targets = ["x86_64-unknown-linux-gnu", "aarch64-apple-darwin"]
93114

94115
[unify]
95-
pin_transitives = false # Enable for hakari/workspace-hack replacement
96-
prune_dead_features = true # Remove features never enabled in graph
97-
detect_unused = true # Find deps not in resolved graph
98-
remove_unused = true # Auto-remove unused deps
99-
msrv = true # Compute workspace MSRV from deps
116+
pin_transitives = false # Enable for hakari/workspace-hack replacement
117+
prune_dead_features = true # Remove empty no-op features
118+
detect_unused = true # Find deps not in resolved graph
119+
remove_unused = true # Auto-remove unused deps
120+
msrv = true # Compute MSRV from resolved graph
121+
major_version_conflict = "warn" # "warn" (skip) or "bump" (force highest)
100122

101123
[release]
102124
tag_format = "{crate}-{prefix}{version}"
@@ -116,12 +138,12 @@ Full reference: [docs/config.md](docs/config.md)
116138

117139
---
118140

119-
## Real-World Impact
141+
## Tested On
120142

121-
`cargo rail unify` on tested monorepos:
143+
`cargo rail unify` results on real monorepos:
122144

123-
| Repository | Crates | Deps Unified | Edits Saved |
124-
|------------|--------|--------------|-------------|
145+
| Repository | Crates | Deps Unified | Member Edits |
146+
|------------|--------|--------------|--------------|
125147
| [tikv](https://github.com/tikv/tikv) | 83 | 57 | 516 |
126148
| [meilisearch](https://github.com/meilisearch/meilisearch) | 19 | 46 | 209 |
127149
| [helix](https://github.com/helix-editor/helix) | 13 | 16 | 66 |
@@ -137,14 +159,26 @@ See [examples/](examples/) for full results across 12 repositories.
137159
| Tool | cargo-rail equivalent |
138160
|------|----------------------|
139161
| cargo-hakari | `unify` with `pin_transitives = true` |
140-
| cargo-udeps / cargo-machete | `detect_unused = true`, `remove_unused = true` |
141-
| cargo-msrv | `msrv = true` |
142-
| cargo-release / release-plz | `release` command |
162+
| cargo-udeps, cargo-machete, cargo-shear | `detect_unused = true` |
163+
| cargo-msrv (for dep-driven MSRV) | `msrv = true` |
164+
| cargo-release, release-plz | `release` command |
143165
| git-cliff | Built-in changelog generation |
144166
| Copybara | `split` + `sync` commands |
145167

146168
---
147169

170+
## Design
171+
172+
**11 dependencies, ~100 resolved.** cargo-hakari pulls ~40 direct via guppy. release-plz pulls 600+ resolved.
173+
174+
**Multi-target resolution.** Queries Cargo's resolver per target triple. Computes feature intersection, not union.
175+
176+
**System git.** Uses `git` binary directly. No libgit2/gitoxide. Deterministic SHAs. git-notes for commit mapping.
177+
178+
**Lossless TOML.** Uses `toml_edit` to preserve comments and formatting.
179+
180+
---
181+
148182
## Installation
149183

150184
```bash

0 commit comments

Comments
 (0)