From f5037c5ae6f4a1ac36f30e4a50c1a5f953b75736 Mon Sep 17 00:00:00 2001
From: Fabio Valentini <decathorpe@gmail.com>
Date: Apr 03 2024 22:08:43 +0000
Subject: Rust: clarifications and docs for %cargo_install_{bin,lib} macros


---

diff --git a/guidelines/modules/ROOT/pages/Rust.adoc b/guidelines/modules/ROOT/pages/Rust.adoc
index 8047681..6bbea2c 100644
--- a/guidelines/modules/ROOT/pages/Rust.adoc
+++ b/guidelines/modules/ROOT/pages/Rust.adoc
@@ -1,6 +1,6 @@
 = Rust Packaging Guidelines
 
-:last-reviewed: 2024-03-14
+:last-reviewed: 2024-04-03
 
 https://www.rust-lang.org[Rust] is a strongly and statically typed,
 compiled programming language
@@ -215,6 +215,9 @@ was added in version 25 of cargo-rpm-macros and rust2rpm.
   An RPM generator parses this file
   and generates appropriate virtual `Provides` for all bundled crates,
   as is required for any bundled dependencies.
+*  Packages that build with vendored dependencies
+  *MUST NOT* provide a Rust library interface (i.e. in `-devel` subpackages),
+  because the resulting packages would have broken dependencies.
 
 Typically, the `%prep` scriptlet will look like this
 when using vendored dependencies
@@ -310,7 +313,7 @@ with both the general and the Rust Packaging Guidelines.
 
 Additionally, due to some properties of packages for Rust crates
 (i.e. subpackages that correspond to crate features / optional dependencies),
-it is necessary to re-run https://pagure.io/fedora-rust/rust2rpm[rust2rpm]
+https://pagure.io/fedora-rust/rust2rpm[rust2rpm] *MUST* be re-run
 for every new version of a crate
 to ensure that generated feature subpackages
 stays in sync with crate metadata.
@@ -319,17 +322,54 @@ stays in sync with crate metadata.
 
 The canonical source of Rust crates is https://crates.io[crates.io].
 
-Rust crates that are published on https://crates.io[crates.io]
+==== Crates with Rust library interface
+
+Crates that are published on https://crates.io[crates.io]
+and that are intended to provide a Rust library interface
 *MUST* be packaged with `rust-$crate` as the name of the source package
 (where `$crate` is the name of the project on https://crates.io[crates.io]).
-Packages for Rust crates that are generated with https://pagure.io/fedora-rust/rust2rpm[rust2rpm]
-follow to this pattern.
+This ensures that there are no name collisions
+between Rust crates published on https://crates.io[crates.io]
+and Rust crates packaged for Fedora.
 
-On the other hand,
-projects from other sources *MUST NOT* use the `rust-` prefix for source package names,
+Projects from sources other than https://crates.io[crates.io]
+*MUST NOT* use the `rust-` prefix for source package names,
 and *MUST* follow the general Naming Guidelines instead.
-They also *MUST NOT* have any virtual `Provides` for Rust crates
-(i.e. `Provides: crate(%{crate}) = %{version}`).
+In this case, the guidelines for either
+link:#_rust_applications_non_crates_io_crates[single-crate Rust applications] or
+link:#_rust_applications_cargo_workspace_projects[cargo workspaces] apply.
+
+If a crate is also part of a larger project
+and it is not feasible to package the Rust crate separately,
+the Rust crate *MAY* be packaged from different sources
+(i.e. an upstream tarball) _if and only if_ the crate
+is also published on https://crates.io[crates.io]
+under the same name and with matching versions.
+
+In this case, the subpackage(s) that contain the Rust crate sources
+*MUST* be named `rust-$crate-devel`
+and `rust-$crate+$feature-devel` for all crate features
+and ensure that the virtual `Provides` for the Rust crate are correct.
+The `rust-` prefix is not required for the name of the source package.
+
+==== Crates without Rust library interface
+
+Crates that do not provide a Rust library interface
+(for example, crates that only contain executable targets)
+*MAY* drop the `rust-` prefix for the name of the source package
+or use the "project name" if it is different from the crate name
+_if and only if_ the project will not provide (or need to provide)
+a Rust library interface in the future,
+since this would require renaming the source package to `rust-$crate`.
+In this case, the guidelines for
+link:#_rust_applications_non_crates_io_crates[single-crate Rust applications] apply,
+and the package is not required to use the sources
+that are published on https://crates.io[crates.io].
+
+When building a crate with vendored dependencies
+the `rust-` prefix of the source package name *MAY* be dropped as well --
+since packages cannot provide a Rust library interface in this case --
+_if and only if_ the project will not need to provide a Rust library interface.
 
 When generating a package for a Rust crate
 that also (or exclusively) contains an application,
@@ -377,14 +417,6 @@ but they *MUST NOT* be used for building the crate itself.
 It is recommended to file an issue with the upstream project
 about including these additional files in published crates.
 
-If a crate is also part of a larger project
-and it is not feasible to package the Rust crate separately,
-the Rust crate *MAY* be packaged as `rust-$crate` from different sources
-(i.e. an upstream tarball) _if and only if_ the crate is also published on https://crates.io[crates.io]
-under the same name and with matching versions.
-In this case, the subpackage(s) corresponding to Rust crates
-*MUST* have correct virtual `Provides` for the Rust crate.
-
 === Crate license
 
 Most tooling support for determining licenses
@@ -436,6 +468,10 @@ is almost entirely automated with several RPM macros:
   they can be moved after calling `%cargo_install`,
   or `%cargo_install` can be replaced
   with manual installation steps.
+  To prevent installation of executables by this macro,
+  the `+%cargo_install_bin+` macro can be defined to `0`.
+  To prevent installation of library sources by this macro,
+  the `+%cargo_install_lib+` macro can be defined to `0`.
 * `%cargo_test`:
   This macro *MUST* be called in the `%check` scriptlet.
   It runs `cargo test` with the appropriate command line arguments.
@@ -741,6 +777,12 @@ i.e. they cannot ship `-devel` subpackages
 that contain crate sources or have subpackages
 that have virtual provides for `crate(...) = %{version}`.
 
+To prevent the `+%cargo_install+` macro
+from installing library sources into `%{cargo_registry}`,
+the `%cargo_install_lib` macro can be defined to `0`.
+When using rust2rpm with a path to a Cargo.toml file
+this macro definition is injected automatically.
+
 === Package naming
 
 Rust applications that are "crates"

