Rust 1.74 gives Cargo a configurable registry credential path
Cargo can now use credential providers for authenticated registry operations. Rust 1.74 also moves lint policy into manifests, making two previously external configuration concerns more explicit.
A private package registry needs to protect reads as well as publication. Its client also needs a defined way to obtain credentials without assuming that a plaintext file is the right storage mechanism. Rust 1.74, released November 16, connects those concerns through authenticated registries and Cargo credential providers.
Registries can now require authentication for all operations. A private registry using this capability requires a configured credential provider. Providers can use operating-system storage or an external implementation, so credential acquisition is a separate operation with an explicit configuration path.
I find this useful because dependency infrastructure should have a clear account of how credentials reach a client. A token's storage and retrieval mechanism affects the build environment independently of the Rust code being compiled. The new provider interface gives that mechanism a supported place in Cargo's configuration.
A provider owns storage and retrieval
The Cargo manual shipped with Rust 1.74 defines credential providers as built-in implementations or external executables. Cargo uses them to store and retrieve credentials. The private-registry configuration requirement is intended to prevent users from unknowingly putting unencrypted credentials on disk.
Built-in providers include macOS Keychain, Windows Credential Manager and libsecret on Linux. The older token provider remains available and stores tokens in Cargo's credentials file without encryption. Selecting the provider therefore has a concrete effect on where the secret resides, rather than merely renaming an existing token setting.
The manual recommends a global provider list in Cargo's user configuration. Its macOS example combines the token provider with the Keychain provider.
[registry]
global-credential-providers = ["cargo:token", "cargo:macos-keychain"]
The analogous Linux and Windows examples select cargo:libsecret and cargo:wincred. A registry can also recommend its own provider. This allows the credential mechanism to fit a service's requirements while keeping the registry's identity and the method used to obtain authorization conceptually separate.
The configuration is sensitive even when it contains no token value. It selects code that can retrieve or store authorization material. Reviewing the provider list is consequently part of understanding the build environment's access to private dependencies.
Environment tokens depend on a selected provider
The manual states that cargo:token checks CARGO_REGISTRIES_<NAME>_TOKEN when retrieving a token. If that provider is absent from the configuration, those token environment variables do not work. This is an important detail for automated builds migrating to an explicit provider list.
An environment variable can be present while the configured retrieval path never consults it. A failed authenticated operation does not necessarily mean the variable was misspelled or the token rejected by the server. The client may have selected a provider that obtains credentials elsewhere.
This distinction improves the diagnosis when it remains visible. The relevant questions are which registry the operation targets and which configured provider is supposed to supply its token. Inspecting the configuration can answer those questions without printing the secret itself.
Public registries retain a historical compatibility behavior. The manual says they do not require explicit provider configuration and use cargo:token when no providers are configured. That differs from the explicit requirement for authenticated alternative registries, so one successful public-registry operation does not establish that a private-registry setup is complete.
External providers support other credential systems
Cargo can invoke an executable implementing its credential-provider protocol. The configuration names the executable and any arguments. This allows other storage or token-generation systems to integrate without requiring Cargo to implement every service's credential policy internally.
A separate built-in adapter, cargo:token-from-stdout, runs a command and uses its standard output as the token. The manual specifies trimming newlines, inheriting standard input and error, and using the exit status to indicate success. That adapter does not support Cargo's login and logout operations.
Those details define an interface, including what the command may assume about its environment. The registry index URL is supplied to it, while an optional registry name is explicitly unsuitable as a lookup key. A provider should identify the registry through the input intended for that purpose.
I prefer this separation to every build script maintaining an unrelated token-fetching convention. The provider can integrate with an existing credential system while Cargo remains responsible for the registry operation. Each part has an interface that can be documented and inspected.
Provider invocation also has a configuration parsing rule. Values in the global list are split on spaces into an executable path and arguments. The manual directs users to credential-alias when paths or arguments themselves contain spaces. This is worth preserving in an integration because the string in the configuration is not an arbitrary shell command with every possible quoting behavior.
A provider can also fail independently of the registry. The command adapter requires a successful exit before its output can supply the token. That gives the credential operation a failure boundary before Cargo performs the authenticated request, which helps distinguish local retrieval problems from remote authorization responses.
Lint policy gains a manifest representation
The same release makes another configuration concern more explicit. Cargo.toml now supports lint tables for the compiler and tools such as Clippy. The announcement contrasts this with build-wide RUSTFLAGS and crate-level attributes. Cargo can carry package policy in the manifest and track changes when deciding what needs rebuilding.
[lints.rust]
unsafe_code = "forbid"
[lints.clippy]
enum_glob_use = "deny"
Workspaces can define a shared policy under workspace.lints, with members opting into inheritance through lints.workspace = true. That makes the relationship between a shared default and a member's adoption explicit. Defining a workspace table and assuming every member uses it would omit the inheritance step the release describes.
The lint levels retain their established meanings, including allow, warn, deny and forbid. The new capability concerns where Cargo obtains the policy and how it applies it. A manifest can now state a package's lint requirements alongside other build metadata, instead of requiring a reader to reconstruct them entirely from ambient flags.
Credential providers and lint tables address different subjects, but both reduce reliance on implicit build environment assumptions. One states how Cargo obtains registry authorization. The other states package-level diagnostic policy. Understanding the resulting build requires reading those explicit settings together with the toolchain version that supports them.