diff --git a/posts/inside-rust/2024-05-07-this-development-cycle-in-cargo-1.79.md b/posts/inside-rust/2024-05-07-this-development-cycle-in-cargo-1.79.md new file mode 100644 index 000000000..7dc2799ed --- /dev/null +++ b/posts/inside-rust/2024-05-07-this-development-cycle-in-cargo-1.79.md @@ -0,0 +1,458 @@ +--- +layout: post +title: "This Development-cycle in Cargo: 1.79" +author: Ed Page +team: The Cargo Team +--- + +# This Development-cycle in Cargo: 1.79 + +This is a summary of what has been happening around Cargo development for the last 6 weeks which is approximately the merge window for Rust 1.79. + + + +- [Plugin of the cycle](#plugin-of-the-cycle) +- [Implementation](#implementation) + - [Deprecations](#deprecations) + - [User-controlled diagnostics](#user-controlled-cargo-diagnostics) + - [MSRV-aware Cargo](#msrv-aware-cargo) + - [Edition 2024](#edition-2024) + - [Normalizing Published Package Files](#normalizing-published-package-files) + - [`cargo info`](#cargo-info) +- [Design discussions](#design-discussions) + - [Applying patch files to dependencies](#applying-patch-files-to-dependencies) + - [Cargo script](#cargo-script) + - [SBOM](#sbom) + - [Nested packages](#nested-packages) + - [Workspace inheritance of deps](#workspace-inheritance-of-deps) +- [Misc](#misc) +- [Focus areas without progress](#focus-areas-without-progress) + +## Plugin of the cycle + +Cargo can't be everything to everyone, +if for no other reason than the compatibility guarantees it must uphold. +Plugins play an important part of the Cargo ecosystem and we want to celebrate them. + +Our plugin for this cycle is [cargo-outdated](https://crates.io/crates/cargo-outdated) which gives an overview of out-of-date dependencies. +As of Cargo 1.78, we include some of this information in the `cargo-update` output +([#13372](https://github.com/rust-lang/cargo/pull/13372)). +Try giving `cargo update --dry-run --verbose` a try! +As for how we could further improve our reporting of outdated dependencies, +see [#4309](https://github.com/rust-lang/cargo/issues/4309). + +Thanks to [LukeMathWalker](https://github.com/LukeMathWalker) for the suggestion! + +[Please submit your suggestions for the next post.](https://rust-lang.zulipchat.com/#narrow/stream/246057-t-cargo/topic/Plugin.20of.20the.20Dev.20Cycle/near/420703211) + +## Implementation + +##### Deprecations + +*[Update from 1.78](https://blog.rust-lang.org/inside-rust/2024/03/26/this-development-cycle-in-cargo-1.78.html#deprecated-cargotoml-fields)* + +[weihanglo](https://github.com/weihanglo/) dug into the cargo code base to enumerate official and unofficial deprecations and recorded them in +[#13629](https://github.com/rust-lang/cargo/issues/13629). + + +The deprecations ended up being divided into the following categories: + +**Deprecate, remove on next Edition:** including [#13747](https://github.com/rust-lang/cargo/pull/13747), [#13804](https://github.com/rust-lang/cargo/pull/13804), and [#13839](https://github.com/rust-lang/cargo/pull/13839). + +**Deprecate but never remove:** This is targeted in areas like the CLI or `.cargo/config.toml` which don't have an Edition mechanism to evolve them. + +**Remove, breaking compatibility:** This is focused on bugs with minimized impact to users. + +An easy example is `badges.workspace = true` allowing inheritance from `package.badges`. +This was not in the RFC, undocumented, and didn't follow the standard pattern for inheritance making it harder to discover. +We removed support for this in [#13788](https://github.com/rust-lang/cargo/pull/13788). + + +Cargo also allowed dependencies without a source (e.g. `dep = {}`). +This was originally removed 3 years ago in [#9686](https://github.com/rust-lang/cargo/pull/9686) +but was reverted after it was reported to have broken an old version of the `bit-set` crate which was used by `libusb` which has gone unmaintained ([see #9885](https://github.com/rust-lang/cargo/issues/9885)). +We revisited this and decided to remove support for it again +(see [#13775](https://github.com/rust-lang/cargo/pull/13775)) +and soon after a user of libusb noticed again +([#13824](https://github.com/rust-lang/cargo/issues/13824)). +After looking at this more carefully, we decided to stick with our original decision. +We broke people 3 years ago, been warning since that it will be removed, and there are two maintained replacement packages +([rusb](https://crates.io/crates/rusb) and [nusb](https://crates.io/crates/nusb)). + +**Re-evaluate in the future:** In particular, for [#4797](https://github.com/rust-lang/cargo/pull/4797), we want to wait until there is a stable mechanism to replace it. + +##### User-controlled cargo diagnostics + +*[Update from 1.78](https://blog.rust-lang.org/inside-rust/2024/03/26/this-development-cycle-in-cargo-1.78.html#user-controlled-cargo-diagnostics). In summary, this aims to add [user-controlled cargo lints](https://github.com/rust-lang/cargo/issues/12235) that look like rustc and are controlled through the [`[lints]` table](https://doc.rust-lang.org/cargo/reference/manifest.html#the-lints-section)* + +[Muscraft](https://github.com/Muscraft) started off this development cycle with a rough sketch of lint system ([#13621](https://github.com/rust-lang/cargo/pull/13621)) and fleshed it out and polished it up including +- Reporting why a lint is being shown ([#13801](https://github.com/rust-lang/cargo/pull/13801)) +- Handling `forbid`'s special behavior ([#13797](https://github.com/rust-lang/cargo/pull/13797/commits)) +- Support for unstable lints ([#13805](https://github.com/rust-lang/cargo/pull/13805)) + + +Original lint names were written using kebab-case. +In [#13635](https://github.com/rust-lang/cargo/pull/13635), +they were switched to also support snake_case to match rustc. +After we had to deal with deprecating snake_case fields in `Cargo.toml`, +[Muscraft](https://github.com/Muscraft) brought up whether we should initially only support one case. +A couple of the participants stylistically preferred kebab-case, especially to match the rest of the manifest. +However, rustc considers snake_case to be the canonical form and we decided that would be a good starting point +([#13837](https://github.com/rust-lang/cargo/pull/13837)). +We can always add a second style later, if we so wished. + + +Our test case for this functionality is deprecating implicit features in Edition 2024. +We modeled this as a deprecation warning for implicit features in existing Editions +while Edition 2024 will report the optional dependency as unused ([#13778](https://github.com/rust-lang/cargo/pull/13778)). +We discussed how we wanted to model unused optional dependemncies. +At a high level, the most direct way is we change how we internally enumerate features to be based on the edition. +However, this doesn't play well with registry packages. +We resolve them off of the Index which doesn't have the full `Cargo.toml`, particularly the Edition, +and prior versions of Cargo would read these Index entries and generate implicit features, breaking on upgrade of Cargo without extra care. +Maybe we should work to support the Edition in the Index but we don't need to do that now. +We ended up stripping unused optional dependencies from the published `Cargo.toml` and the Index. +The way this was done also means they won't show up in `Cargo.lock` like unused `workspace.dependencies`. +As a side effect, some lints may not run against these dependencies. + +![rendering of unused optional dependency lint](../../../../images/inside-rust/2024-05-07-this-development-cycle-in-cargo-1.79/lint.stdout.term.svg) + +##### MSRV-aware Cargo + +*[Update from 1.78](https://blog.rust-lang.org/inside-rust/2024/03/26/this-development-cycle-in-cargo-1.78.html#msrv-aware-cargo)* + +The subset needed for Edition 2024 is effectively code complete! +Feel free to [try it out](https://doc.rust-lang.org/nightly/cargo/reference/unstable.html#msrv-aware-resolver) +and [leave feedback](https://github.com/rust-lang/cargo/issues/9930). + +We continued to iterate on how we report lockfile changes, including +- Reporting that dependencies changed on any command, not just `update` ([#13561](https://github.com/rust-lang/cargo/pull/13561), [#13759](https://github.com/rust-lang/cargo/pull/13759)) + +We've continued to iterate on the MSRV resolver's behavior, including +- Defaulting to `rustc -V` when your `package.rust-version` is unset ([#13743](https://github.com/rust-lang/cargo/pull/13743)) +- Tweaked the behavior when a dependency's `package.rust-version` is unset ([#13791](https://github.com/rust-lang/cargo/pull/13791)) +- Avoiding it for `cargo install` ([#13790](https://github.com/rust-lang/cargo/pull/13790)) + +As for controlling the resolver policy, we've implemented: +- `--ignore-rust-version` disables MSRV dependency resolution ([#13738](https://github.com/rust-lang/cargo/pull/13738)) +- We added `--ignore-rust-version` to `cargo update` and `cargo generate-lockfile` ([#13742](https://github.com/rust-lang/cargo/pull/13742)) +- We added a placeholder config field so it can be forced on or off ([#13769](https://github.com/rust-lang/cargo/pull/13769)). We still need final names for this, see [#13540](https://github.com/rust-lang/cargo/issues/13540). +- We added `package.resolver = "3"` ([#13776](https://github.com/rust-lang/cargo/pull/13776)) +- We made this the default resolver for Edition 2024 ([#13785](https://github.com/rust-lang/cargo/pull/13785)) + +##### Edition 2024 + +*[Update from 1.76](https://blog.rust-lang.org/inside-rust/2024/01/03/this-development-cycle-in-cargo-1-76.html#meta-2024-edition)* + +In addition to the above, work on Editions draws more attention to `cargo fix`. +This includes [#13728](https://github.com/rust-lang/cargo/pull/13728) and [#13792](https://github.com/rust-lang/cargo/pull/13792) +by [weihanglo](https://github.com/weihanglo/). + +We also discussed [on Zulip](https://rust-lang.zulipchat.com/#narrow/stream/246057-t-cargo/topic/.60cargo.20fix.20--edition.60.20and.20.60Cargo.2Etoml.60.20changes) if there are `Cargo.toml` changes that should be made by `cargo fix --edition`, like updating the `package.edition` or the `package.rust-version`. + +The challenge with updating `package.edition` is `cargo fix` only runs for one set of build targets, platforms, and feature combinations and so we don't know when an entire project is fully converted over to the new edition. +The user might need to make multiple calls to migrate and updating `package.edition` too early can get in the way of that. + +##### Normalizing Published Package Files + +*[Update from 1.78](https://blog.rust-lang.org/inside-rust/2024/03/26/this-development-cycle-in-cargo-1.78.html#performance)* + +After much work ( +[#13666](https://github.com/rust-lang/cargo/pull/13666) +[#13693](https://github.com/rust-lang/cargo/pull/13693) +[#13701](https://github.com/rust-lang/cargo/pull/13701) +[#13713](https://github.com/rust-lang/cargo/pull/13713) +[#13729](https://github.com/rust-lang/cargo/pull/13729) +), published and vendored `Cargo.toml` files will now include all build targets explicitly enumerated. + +Benefits +- You cannot bypass the checksum in adding a build target to a vendored dependency by dropping a file +- When all build targets have an explicit path, you now get a warning if one is excluded when packing, helping to catch mistakes +- You can now intentionally exclude a build target from publishing without having to set the path +- It is easier to audit changes to the build targets across versions +- We hope this opens the door to more performance improvements when parsing large dependency trees + +As a side effect, the output from `cargo vendor` will vary by Cargo version. +We try to minimize this kind of churn but felt it was justified in this case. + +##### `cargo info` + +*[Update from 1.76](https://blog.rust-lang.org/inside-rust/2024/01/03/this-development-cycle-in-cargo-1-76.html#cargo-info)* + +There was some recent discussion on an issue for how `cargo add` should render features +([#10681](https://github.com/rust-lang/cargo/issues/10681)). +epage figured `cargo info` could be a good place to try out their proposal +([cargo-information#140](https://github.com/hi-rustin/cargo-information/pull/140)). +A question aspect of this was to apply the same rendering to dependencies to distinguish between required, activated-optional, and deactivated-optional dependencies. + +epage also made the auto-selection of what version to show a little smarter. +Instead of showing the latest when a version is unspecified, +`cargo info` tries to be smart and show you a version that is relevant. +Before, that was a version from your lockfile or a MSRV-compatible version. +With [cargo-information#137](https://github.com/hi-rustin/cargo-information/pull/137), +we don't just check the lockfile but first check the direct dependencies of the package you are in and then the direct dependencies of all workspace members, making it more likely what will be shown is what you will be using. + +![rendering of cargo-info's verbose output using SVG](../../../../images/inside-rust/2024-05-07-this-development-cycle-in-cargo-1.79/info.stdout.term.svg) +*(verbose output, normally dependencies are hidden)* + +At this point, [`cargo-information`](https://crates.io/crates/cargo-information) feels like it could be ready to merge into cargo. +Please give it a try and [let us know what you think](https://github.com/hi-rustin/cargo-information/issues)! + +## Design discussions + +#### Applying patch files to dependencies + +*[Update from 1.76](https://blog.rust-lang.org/inside-rust/2024/01/03/this-development-cycle-in-cargo-1-76.html#postponing-rfcs)* + +Previously, we discussed closing this RFC, asking for an experimental implementation to help flesh out the design. +[weihanglo](https://github.com/weihanglo/) stepped in with a proof of concept in [#13779](https://github.com/rust-lang/cargo/pull/13779). +High level design discussions are on-going on that PR. + +#### Cargo script + +*[Update from 1.77](https://blog.rust-lang.org/inside-rust/2024/02/13/this-development-cycle-in-cargo-1-77.html#cargo-script)* + +T-lang has approved [RFC #3503](https://github.com/rust-lang/rfcs/pull/3503) for the syntax of embedding manifests. +This still leaves [RFC #3502](https://github.com/rust-lang/rfcs/pull/3502). + + +While cargo script is primarily focused on exploration, +there will be times people want to do heavy analysis and want release builds (see [RFC comment](https://github.com/rust-lang/rfcs/pull/3502#discussion_r1337996703)). + +We could add `cargo --release