From b770639c91abd6c5003ae3c9242e6c7ec37b3dff Mon Sep 17 00:00:00 2001 From: Charlie Marsh Date: Sun, 14 Sep 2025 09:27:45 -0400 Subject: [PATCH] Rename `provides_extras` to `provides_extra` (#15825) ## Summary This is now consistent with `requires_dist` (singular). --- crates/uv-build-backend/src/metadata.rs | 2 +- crates/uv-cache/src/lib.rs | 2 +- crates/uv-client/src/registry_client.rs | 2 +- .../src/dependency_metadata.rs | 8 ++--- crates/uv-distribution/src/metadata/mod.rs | 10 +++---- .../src/metadata/requires_dist.rs | 10 +++---- crates/uv-publish/src/lib.rs | 4 +-- .../uv-pypi-types/src/metadata/metadata23.rs | 8 ++--- .../src/metadata/metadata_resolver.rs | 23 +++++++------- .../src/metadata/requires_dist.rs | 11 +++---- .../src/metadata/requires_txt.rs | 16 +++++----- crates/uv-pypi-types/src/simple_json.rs | 4 +-- crates/uv-requirements/src/extras.rs | 2 +- crates/uv-requirements/src/source_tree.rs | 4 +-- crates/uv-resolver/src/lock/mod.rs | 30 +++++++++---------- ...r__lock__tests__hash_optional_missing.snap | 2 +- ...r__lock__tests__hash_optional_present.snap | 2 +- ...r__lock__tests__hash_required_present.snap | 2 +- ...missing_dependency_source_unambiguous.snap | 4 +-- ...dependency_source_version_unambiguous.snap | 4 +-- ...s__missing_dependency_version_dynamic.snap | 6 ++-- ...issing_dependency_version_unambiguous.snap | 4 +-- ...lock__tests__source_direct_has_subdir.snap | 2 +- ..._lock__tests__source_direct_no_subdir.snap | 2 +- ...solver__lock__tests__source_directory.snap | 2 +- ...esolver__lock__tests__source_editable.snap | 2 +- crates/uv-resolver/src/resolution/output.rs | 2 +- crates/uv-settings/src/settings.rs | 4 +-- crates/uv/tests/it/cache_clean.rs | 4 +-- crates/uv/tests/it/lock.rs | 2 +- docs/reference/settings.md | 4 +-- uv.schema.json | 6 ++-- 32 files changed, 94 insertions(+), 96 deletions(-) diff --git a/crates/uv-build-backend/src/metadata.rs b/crates/uv-build-backend/src/metadata.rs index 714717a76..fd2bd3401 100644 --- a/crates/uv-build-backend/src/metadata.rs +++ b/crates/uv-build-backend/src/metadata.rs @@ -547,7 +547,7 @@ impl PyProjectToml { license_files, classifiers: self.project.classifiers.clone().unwrap_or_default(), requires_dist: requires_dist.iter().map(ToString::to_string).collect(), - provides_extras: extras.iter().map(ToString::to_string).collect(), + provides_extra: extras.iter().map(ToString::to_string).collect(), // Not commonly set. provides_dist: vec![], // Not supported. diff --git a/crates/uv-cache/src/lib.rs b/crates/uv-cache/src/lib.rs index 1b52edd9e..dc8bea8c6 100644 --- a/crates/uv-cache/src/lib.rs +++ b/crates/uv-cache/src/lib.rs @@ -1002,7 +1002,7 @@ impl CacheBucket { Self::Interpreter => "interpreter-v4", // Note that when bumping this, you'll also need to bump it // in `crates/uv/tests/it/cache_clean.rs`. - Self::Simple => "simple-v17", + Self::Simple => "simple-v18", // Note that when bumping this, you'll also need to bump it // in `crates/uv/tests/it/cache_prune.rs`. Self::Wheels => "wheels-v5", diff --git a/crates/uv-client/src/registry_client.rs b/crates/uv-client/src/registry_client.rs index 2e21c9bb6..4fec985f0 100644 --- a/crates/uv-client/src/registry_client.rs +++ b/crates/uv-client/src/registry_client.rs @@ -1245,7 +1245,7 @@ impl SimpleMetadata { version: version.clone(), requires_dist: metadata.requires_dist, requires_python: metadata.requires_python, - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dynamic: false, }); SimpleMetadatum { diff --git a/crates/uv-distribution-types/src/dependency_metadata.rs b/crates/uv-distribution-types/src/dependency_metadata.rs index 1e978db3d..825ad630d 100644 --- a/crates/uv-distribution-types/src/dependency_metadata.rs +++ b/crates/uv-distribution-types/src/dependency_metadata.rs @@ -49,7 +49,7 @@ impl DependencyMetadata { version: version.clone(), requires_dist: metadata.requires_dist.clone(), requires_python: metadata.requires_python.clone(), - provides_extras: metadata.provides_extras.clone(), + provides_extra: metadata.provides_extra.clone(), dynamic: false, }) } else { @@ -70,7 +70,7 @@ impl DependencyMetadata { version, requires_dist: metadata.requires_dist.clone(), requires_python: metadata.requires_python.clone(), - provides_extras: metadata.provides_extras.clone(), + provides_extra: metadata.provides_extra.clone(), dynamic: false, }) } @@ -109,6 +109,6 @@ pub struct StaticMetadata { ) )] pub requires_python: Option, - #[serde(default)] - pub provides_extras: Box<[ExtraName]>, + #[serde(default, alias = "provides-extras")] + pub provides_extra: Box<[ExtraName]>, } diff --git a/crates/uv-distribution/src/metadata/mod.rs b/crates/uv-distribution/src/metadata/mod.rs index 5deb37c03..0e393be48 100644 --- a/crates/uv-distribution/src/metadata/mod.rs +++ b/crates/uv-distribution/src/metadata/mod.rs @@ -58,7 +58,7 @@ pub struct Metadata { // Optional fields pub requires_dist: Box<[Requirement]>, pub requires_python: Option, - pub provides_extras: Box<[ExtraName]>, + pub provides_extra: Box<[ExtraName]>, pub dependency_groups: BTreeMap>, pub dynamic: bool, } @@ -74,7 +74,7 @@ impl Metadata { .map(Requirement::from) .collect(), requires_python: metadata.requires_python, - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dependency_groups: BTreeMap::default(), dynamic: metadata.dynamic, } @@ -94,13 +94,13 @@ impl Metadata { let requires_dist = uv_pypi_types::RequiresDist { name: metadata.name, requires_dist: metadata.requires_dist, - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dynamic: metadata.dynamic, }; let RequiresDist { name, requires_dist, - provides_extras, + provides_extra, dependency_groups, dynamic, } = RequiresDist::from_project_maybe_workspace( @@ -119,7 +119,7 @@ impl Metadata { version: metadata.version, requires_dist, requires_python: metadata.requires_python, - provides_extras, + provides_extra, dependency_groups, dynamic, }) diff --git a/crates/uv-distribution/src/metadata/requires_dist.rs b/crates/uv-distribution/src/metadata/requires_dist.rs index e2f342234..7df61bb21 100644 --- a/crates/uv-distribution/src/metadata/requires_dist.rs +++ b/crates/uv-distribution/src/metadata/requires_dist.rs @@ -19,7 +19,7 @@ use crate::metadata::{GitWorkspaceMember, LoweredRequirement, MetadataError}; pub struct RequiresDist { pub name: PackageName, pub requires_dist: Box<[Requirement]>, - pub provides_extras: Box<[ExtraName]>, + pub provides_extra: Box<[ExtraName]>, pub dependency_groups: BTreeMap>, pub dynamic: bool, } @@ -33,7 +33,7 @@ impl RequiresDist { requires_dist: Box::into_iter(metadata.requires_dist) .map(Requirement::from) .collect(), - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dependency_groups: BTreeMap::default(), dynamic: metadata.dynamic, } @@ -198,7 +198,7 @@ impl RequiresDist { name: metadata.name, requires_dist, dependency_groups, - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dynamic: metadata.dynamic, }) } @@ -216,7 +216,7 @@ impl RequiresDist { for source in sources.iter() { if let Some(extra) = source.extra() { // If the extra doesn't exist at all, error. - if !metadata.provides_extras.contains(extra) { + if !metadata.provides_extra.contains(extra) { return Err(MetadataError::MissingSourceExtra( name.clone(), extra.clone(), @@ -268,7 +268,7 @@ impl From for RequiresDist { Self { name: metadata.name, requires_dist: metadata.requires_dist, - provides_extras: metadata.provides_extras, + provides_extra: metadata.provides_extra, dependency_groups: metadata.dependency_groups, dynamic: metadata.dynamic, } diff --git a/crates/uv-publish/src/lib.rs b/crates/uv-publish/src/lib.rs index a1409ccf4..4ab09c4f2 100644 --- a/crates/uv-publish/src/lib.rs +++ b/crates/uv-publish/src/lib.rs @@ -746,7 +746,7 @@ impl FormMetadata { requires_python, requires_external, project_urls, - provides_extras, + provides_extra, dynamic, } = metadata(file, filename).await?; @@ -808,7 +808,7 @@ impl FormMetadata { add_vec("platform", platforms); add_vec("project_urls", project_urls); add_vec("provides_dist", provides_dist); - add_vec("provides_extra", provides_extras); + add_vec("provides_extra", provides_extra); add_vec("requires_dist", requires_dist); add_vec("requires_external", requires_external); diff --git a/crates/uv-pypi-types/src/metadata/metadata23.rs b/crates/uv-pypi-types/src/metadata/metadata23.rs index 811f5773d..79c2043fc 100644 --- a/crates/uv-pypi-types/src/metadata/metadata23.rs +++ b/crates/uv-pypi-types/src/metadata/metadata23.rs @@ -99,7 +99,7 @@ pub struct Metadata23 { /// A string containing the name of an optional feature. Must be a valid Python identifier. /// May be used to make a dependency conditional on whether the optional feature has been /// requested. - pub provides_extras: Vec, + pub provides_extra: Vec, /// A string containing the name of another core metadata field. pub dynamic: Vec, } @@ -145,7 +145,7 @@ impl Metadata23 { let requires_python = headers.get_first_value("Requires-Python"); let requires_external = headers.get_all_values("Requires-External").collect(); let project_urls = headers.get_all_values("Project-URL").collect(); - let provides_extras = headers.get_all_values("Provides-Extra").collect(); + let provides_extra = headers.get_all_values("Provides-Extra").collect(); let description_content_type = headers.get_first_value("Description-Content-Type"); let dynamic = headers.get_all_values("Dynamic").collect(); Ok(Self { @@ -174,7 +174,7 @@ impl Metadata23 { requires_python, requires_external, project_urls, - provides_extras, + provides_extra, dynamic, }) } @@ -264,7 +264,7 @@ impl Metadata23 { ); write_all(&mut writer, "Requires-External", &self.requires_external); write_all(&mut writer, "Project-URL", &self.project_urls); - write_all(&mut writer, "Provides-Extra", &self.provides_extras); + write_all(&mut writer, "Provides-Extra", &self.provides_extra); write_opt_str( &mut writer, "Description-Content-Type", diff --git a/crates/uv-pypi-types/src/metadata/metadata_resolver.rs b/crates/uv-pypi-types/src/metadata/metadata_resolver.rs index 506b7651d..0fe26d11c 100644 --- a/crates/uv-pypi-types/src/metadata/metadata_resolver.rs +++ b/crates/uv-pypi-types/src/metadata/metadata_resolver.rs @@ -31,7 +31,8 @@ pub struct ResolutionMetadata { // Optional fields pub requires_dist: Box<[Requirement]>, pub requires_python: Option, - pub provides_extras: Box<[ExtraName]>, + #[serde(alias = "provides-extras")] + pub provides_extra: Box<[ExtraName]>, /// Whether the version field is dynamic. #[serde(default)] pub dynamic: bool, @@ -64,7 +65,7 @@ impl ResolutionMetadata { .map(|requires_python| LenientVersionSpecifiers::from_str(&requires_python)) .transpose()? .map(VersionSpecifiers::from); - let provides_extras = headers + let provides_extra = headers .get_all_values("Provides-Extra") .filter_map( |provides_extra| match ExtraName::from_owned(provides_extra) { @@ -85,7 +86,7 @@ impl ResolutionMetadata { version, requires_dist, requires_python, - provides_extras, + provides_extra, dynamic, }) } @@ -144,7 +145,7 @@ impl ResolutionMetadata { .map(|requires_python| LenientVersionSpecifiers::from_str(&requires_python)) .transpose()? .map(VersionSpecifiers::from); - let provides_extras = headers + let provides_extra = headers .get_all_values("Provides-Extra") .filter_map( |provides_extra| match ExtraName::from_owned(provides_extra) { @@ -162,7 +163,7 @@ impl ResolutionMetadata { version, requires_dist, requires_python, - provides_extras, + provides_extra, dynamic, }) } @@ -250,7 +251,7 @@ impl ResolutionMetadata { .collect::, _>>()?; // Extract the optional dependencies. - let provides_extras = project + let provides_extra = project .optional_dependencies .unwrap_or_default() .into_keys() @@ -261,7 +262,7 @@ impl ResolutionMetadata { version, requires_dist, requires_python, - provides_extras, + provides_extra, dynamic, }) } @@ -370,7 +371,7 @@ mod tests { assert_eq!(meta.version, Version::new([1, 0])); assert!(meta.requires_python.is_none()); assert!(meta.requires_dist.is_empty()); - assert!(meta.provides_extras.is_empty()); + assert!(meta.provides_extra.is_empty()); let s = r#" [project] @@ -384,7 +385,7 @@ mod tests { assert_eq!(meta.version, Version::new([1, 0])); assert_eq!(meta.requires_python, Some(">=3.6".parse().unwrap())); assert!(meta.requires_dist.is_empty()); - assert!(meta.provides_extras.is_empty()); + assert!(meta.provides_extra.is_empty()); let s = r#" [project] @@ -399,7 +400,7 @@ mod tests { assert_eq!(meta.version, Version::new([1, 0])); assert_eq!(meta.requires_python, Some(">=3.6".parse().unwrap())); assert_eq!(*meta.requires_dist, ["foo".parse().unwrap()]); - assert!(meta.provides_extras.is_empty()); + assert!(meta.provides_extra.is_empty()); let s = r#" [project] @@ -423,6 +424,6 @@ mod tests { "bar; extra == \"dotenv\"".parse().unwrap() ] ); - assert_eq!(*meta.provides_extras, ["dotenv".parse().unwrap()]); + assert_eq!(*meta.provides_extra, ["dotenv".parse().unwrap()]); } } diff --git a/crates/uv-pypi-types/src/metadata/requires_dist.rs b/crates/uv-pypi-types/src/metadata/requires_dist.rs index d24933b9a..6194a7e56 100644 --- a/crates/uv-pypi-types/src/metadata/requires_dist.rs +++ b/crates/uv-pypi-types/src/metadata/requires_dist.rs @@ -1,7 +1,6 @@ use std::str::FromStr; use itertools::Itertools; -use serde::{Deserialize, Serialize}; use uv_normalize::{ExtraName, PackageName}; use uv_pep508::Requirement; @@ -15,13 +14,11 @@ use crate::{LenientRequirement, MetadataError, VerbatimParsedUrl}; /// This is a subset of [`ResolutionMetadata`]; specifically, it omits the `version` and `requires-python` /// fields, which aren't necessary when extracting the requirements of a package without installing /// the package itself. -#[derive(Serialize, Deserialize, Debug, Clone)] -#[serde(rename_all = "kebab-case")] +#[derive(Debug, Clone)] pub struct RequiresDist { pub name: PackageName, pub requires_dist: Box<[Requirement]>, - pub provides_extras: Box<[ExtraName]>, - #[serde(default)] + pub provides_extra: Box<[ExtraName]>, pub dynamic: bool, } @@ -86,7 +83,7 @@ impl RequiresDist { .collect::, _>>()?; // Extract the optional dependencies. - let provides_extras = project + let provides_extra = project .optional_dependencies .unwrap_or_default() .into_keys() @@ -95,7 +92,7 @@ impl RequiresDist { Ok(Self { name, requires_dist, - provides_extras, + provides_extra, dynamic, }) } diff --git a/crates/uv-pypi-types/src/metadata/requires_txt.rs b/crates/uv-pypi-types/src/metadata/requires_txt.rs index 74e63db49..edae35697 100644 --- a/crates/uv-pypi-types/src/metadata/requires_txt.rs +++ b/crates/uv-pypi-types/src/metadata/requires_txt.rs @@ -1,19 +1,19 @@ -use crate::{LenientRequirement, MetadataError, VerbatimParsedUrl}; -use serde::Deserialize; use std::io::BufRead; use std::str::FromStr; + use uv_normalize::ExtraName; use uv_pep508::{ExtraOperator, MarkerExpression, MarkerTree, MarkerValueExtra, Requirement}; +use crate::{LenientRequirement, MetadataError, VerbatimParsedUrl}; + /// `requires.txt` metadata as defined in . /// /// This is a subset of the full metadata specification, and only includes the fields that are /// included in the legacy `requires.txt` file. -#[derive(Deserialize, Debug, Clone)] -#[serde(rename_all = "kebab-case")] +#[derive(Debug, Clone)] pub struct RequiresTxt { pub requires_dist: Vec>, - pub provides_extras: Vec, + pub provides_extra: Vec, } impl RequiresTxt { @@ -22,7 +22,7 @@ impl RequiresTxt { /// See: pub fn parse(content: &[u8]) -> Result { let mut requires_dist = vec![]; - let mut provides_extras = vec![]; + let mut provides_extra = vec![]; let mut current_marker = MarkerTree::default(); for line in content.lines() { @@ -52,7 +52,7 @@ impl RequiresTxt { // Parse the extra. let extra = if let Some(extra) = extra { if let Ok(extra) = ExtraName::from_str(extra) { - provides_extras.push(extra.clone()); + provides_extra.push(extra.clone()); Some(MarkerValueExtra::Extra(extra)) } else { Some(MarkerValueExtra::Arbitrary(extra.to_string())) @@ -103,7 +103,7 @@ impl RequiresTxt { Ok(Self { requires_dist, - provides_extras, + provides_extra, }) } } diff --git a/crates/uv-pypi-types/src/simple_json.rs b/crates/uv-pypi-types/src/simple_json.rs index 92f72de1a..3846626bc 100644 --- a/crates/uv-pypi-types/src/simple_json.rs +++ b/crates/uv-pypi-types/src/simple_json.rs @@ -237,8 +237,8 @@ pub struct CoreMetadatum { pub requires_python: Option, #[serde(default)] pub requires_dist: Box<[Requirement]>, - #[serde(default)] - pub provides_extras: Box<[ExtraName]>, + #[serde(default, alias = "provides-extras")] + pub provides_extra: Box<[ExtraName]>, } #[derive(Debug, Clone)] diff --git a/crates/uv-requirements/src/extras.rs b/crates/uv-requirements/src/extras.rs index 87703a98b..a14c88f2b 100644 --- a/crates/uv-requirements/src/extras.rs +++ b/crates/uv-requirements/src/extras.rs @@ -113,7 +113,7 @@ impl<'a, Context: BuildContext> ExtrasResolver<'a, Context> { // Sort extras for consistency. let extras = { - let mut extras = metadata.provides_extras.to_vec(); + let mut extras = metadata.provides_extra.to_vec(); extras.sort_unstable(); extras }; diff --git a/crates/uv-requirements/src/source_tree.rs b/crates/uv-requirements/src/source_tree.rs index a7a99c5a2..03d146dd7 100644 --- a/crates/uv-requirements/src/source_tree.rs +++ b/crates/uv-requirements/src/source_tree.rs @@ -91,7 +91,7 @@ impl<'a, Context: BuildContext> SourceTreeResolver<'a, Context> { // Determine the extras to include when resolving the requirements. let extras = self .extras - .extra_names(metadata.provides_extras.iter()) + .extra_names(metadata.provides_extra.iter()) .cloned() .collect::>(); @@ -111,7 +111,7 @@ impl<'a, Context: BuildContext> SourceTreeResolver<'a, Context> { let requirements = requirements.into_boxed_slice(); let project = metadata.name; - let extras = metadata.provides_extras; + let extras = metadata.provides_extra; Ok(SourceTreeResolution { requirements, diff --git a/crates/uv-resolver/src/lock/mod.rs b/crates/uv-resolver/src/lock/mod.rs index 6a4633d4d..fed3a623a 100644 --- a/crates/uv-resolver/src/lock/mod.rs +++ b/crates/uv-resolver/src/lock/mod.rs @@ -1229,11 +1229,11 @@ impl Lock { if let Some(requires_python) = metadata.requires_python.as_ref() { table.insert("requires-python", value(requires_python.to_string())); } - if !metadata.provides_extras.is_empty() { + if !metadata.provides_extra.is_empty() { table.insert( "provides-extras", value(serde::Serialize::serialize( - &metadata.provides_extras, + &metadata.provides_extra, toml_edit::ser::ValueSerializer::new(), )?), ); @@ -1332,7 +1332,7 @@ impl Lock { } let expected: BTreeSet<_> = provides_extra.iter().collect(); - let actual: BTreeSet<_> = package.metadata.provides_extras.iter().collect(); + let actual: BTreeSet<_> = package.metadata.provides_extra.iter().collect(); if expected != actual { let expected = Box::into_iter(provides_extra).collect(); @@ -1783,7 +1783,7 @@ impl Lock { } // Validate the `provides-extras` metadata. - match self.satisfies_provides_extra(metadata.provides_extras, package) { + match self.satisfies_provides_extra(metadata.provides_extra, package) { SatisfiesResult::Satisfied => {} result => return Ok(result), } @@ -1824,7 +1824,7 @@ impl Lock { } // Validate that the extras are unchanged. - if let SatisfiesResult::Satisfied = self.satisfies_provides_extra(metadata.provides_extras, package, ) { + if let SatisfiesResult::Satisfied = self.satisfies_provides_extra(metadata.provides_extra, package, ) { debug!("Static `provides-extra` for `{}` is up-to-date", package.id); } else { debug!("Static `provides-extra` for `{}` is out-of-date; falling back to distribution database", package.id); @@ -1905,7 +1905,7 @@ impl Lock { } // Validate that the extras are unchanged. - match self.satisfies_provides_extra(metadata.provides_extras, package) { + match self.satisfies_provides_extra(metadata.provides_extra, package) { SatisfiesResult::Satisfied => {} result => return Ok(result), } @@ -2346,14 +2346,14 @@ impl Package { .collect::>() .map_err(LockErrorKind::RequirementRelativePath)? }; - let provides_extras = if id.source.is_immutable() { + let provides_extra = if id.source.is_immutable() { Box::default() } else { annotated_dist .metadata .as_ref() .expect("metadata is present") - .provides_extras + .provides_extra .clone() }; let dependency_groups = if id.source.is_immutable() { @@ -2386,7 +2386,7 @@ impl Package { dependency_groups: BTreeMap::default(), metadata: PackageMetadata { requires_dist, - provides_extras, + provides_extra, dependency_groups, }, }) @@ -2995,10 +2995,10 @@ impl Package { } } - if !self.metadata.provides_extras.is_empty() { + if !self.metadata.provides_extra.is_empty() { let provides_extras = self .metadata - .provides_extras + .provides_extra .iter() .map(|extra| { serde::Serialize::serialize(&extra, toml_edit::ser::ValueSerializer::new()) @@ -3136,7 +3136,7 @@ impl Package { /// Returns the extras the package provides, if any. pub fn provides_extras(&self) -> &[ExtraName] { - &self.metadata.provides_extras + &self.metadata.provides_extra } /// Returns the dependency groups the package provides, if any. @@ -3211,8 +3211,8 @@ struct PackageWire { struct PackageMetadata { #[serde(default)] requires_dist: BTreeSet, - #[serde(default)] - provides_extras: Box<[ExtraName]>, + #[serde(default, rename = "provides-extras")] + provides_extra: Box<[ExtraName]>, #[serde(default, rename = "requires-dev", alias = "dependency-groups")] dependency_groups: BTreeMap>, } @@ -3235,7 +3235,7 @@ impl PackageMetadata { Self { requires_dist: unwire_requirements(self.requires_dist), - provides_extras: self.provides_extras, + provides_extra: self.provides_extra, dependency_groups: self .dependency_groups .into_iter() diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_missing.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_missing.snap index b5086442b..0a847c0c2 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_missing.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_missing.snap @@ -92,7 +92,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_present.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_present.snap index 26417647e..8c75ee866 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_present.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_optional_present.snap @@ -99,7 +99,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_required_present.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_required_present.snap index 8d7476c02..1daf5a47d 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_required_present.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__hash_required_present.snap @@ -95,7 +95,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_unambiguous.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_unambiguous.snap index c6fe9c4af..17c061494 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_unambiguous.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_unambiguous.snap @@ -84,7 +84,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, @@ -155,7 +155,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_version_unambiguous.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_version_unambiguous.snap index c6fe9c4af..17c061494 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_version_unambiguous.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_source_version_unambiguous.snap @@ -84,7 +84,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, @@ -155,7 +155,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_dynamic.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_dynamic.snap index b023d8238..0870ee298 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_dynamic.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_dynamic.snap @@ -58,7 +58,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, @@ -106,7 +106,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, @@ -171,7 +171,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_unambiguous.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_unambiguous.snap index c6fe9c4af..17c061494 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_unambiguous.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__missing_dependency_version_unambiguous.snap @@ -84,7 +84,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, @@ -155,7 +155,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_has_subdir.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_has_subdir.snap index 59786dddf..70e0a0f71 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_has_subdir.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_has_subdir.snap @@ -67,7 +67,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_no_subdir.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_no_subdir.snap index 337b3fea5..08873c5c4 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_no_subdir.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_direct_no_subdir.snap @@ -65,7 +65,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_directory.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_directory.snap index 2db372e3e..7b15016cc 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_directory.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_directory.snap @@ -60,7 +60,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_editable.snap b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_editable.snap index 4c7642f83..5afb02d76 100644 --- a/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_editable.snap +++ b/crates/uv-resolver/src/lock/snapshots/uv_resolver__lock__tests__source_editable.snap @@ -60,7 +60,7 @@ Ok( dependency_groups: {}, metadata: PackageMetadata { requires_dist: {}, - provides_extras: [], + provides_extra: [], dependency_groups: {}, }, }, diff --git a/crates/uv-resolver/src/resolution/output.rs b/crates/uv-resolver/src/resolution/output.rs index 35968e671..edea7911e 100644 --- a/crates/uv-resolver/src/resolution/output.rs +++ b/crates/uv-resolver/src/resolution/output.rs @@ -358,7 +358,7 @@ impl ResolverOutput { if let Some(metadata) = metadata.as_ref() { // Validate the extra. if let Some(extra) = extra { - if !metadata.provides_extras.contains(extra) { + if !metadata.provides_extra.contains(extra) { diagnostics.push(ResolutionDiagnostic::MissingExtra { dist: dist.clone(), extra: extra.clone(), diff --git a/crates/uv-settings/src/settings.rs b/crates/uv-settings/src/settings.rs index 64bdaf11b..df6ad260a 100644 --- a/crates/uv-settings/src/settings.rs +++ b/crates/uv-settings/src/settings.rs @@ -719,7 +719,7 @@ pub struct ResolverInstallerSchema { /// to all versions of the package. /// - (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`). /// - (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`). - /// - (Optional) `provides-extras`: The extras provided by the package. + /// - (Optional) `provides-extra`: The extras provided by the package. #[option( default = r#"[]"#, value_type = "list[dict]", @@ -1427,7 +1427,7 @@ pub struct PipOptions { /// to all versions of the package. /// - (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`). /// - (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`). - /// - (Optional) `provides-extras`: The extras provided by the package. + /// - (Optional) `provides-extra`: The extras provided by the package. #[option( default = r#"[]"#, value_type = "list[dict]", diff --git a/crates/uv/tests/it/cache_clean.rs b/crates/uv/tests/it/cache_clean.rs index 0678ed996..06fd8f215 100644 --- a/crates/uv/tests/it/cache_clean.rs +++ b/crates/uv/tests/it/cache_clean.rs @@ -51,7 +51,7 @@ fn clean_package_pypi() -> Result<()> { // Assert that the `.rkyv` file is created for `iniconfig`. let rkyv = context .cache_dir - .child("simple-v17") + .child("simple-v18") .child("pypi") .child("iniconfig.rkyv"); assert!( @@ -125,7 +125,7 @@ fn clean_package_index() -> Result<()> { // Assert that the `.rkyv` file is created for `iniconfig`. let rkyv = context .cache_dir - .child("simple-v17") + .child("simple-v18") .child("index") .child("e8208120cae3ba69") .child("iniconfig.rkyv"); diff --git a/crates/uv/tests/it/lock.rs b/crates/uv/tests/it/lock.rs index 339a61578..7f7372fcc 100644 --- a/crates/uv/tests/it/lock.rs +++ b/crates/uv/tests/it/lock.rs @@ -20009,7 +20009,7 @@ fn lock_dependency_metadata() -> Result<()> { | 11 | requires_dist = ["typing-extensions"] | ^^^^^^^^^^^^^ - unknown field `requires_dist`, expected one of `name`, `version`, `requires-dist`, `requires-python`, `provides-extras` + unknown field `requires_dist`, expected one of `name`, `version`, `requires-dist`, `requires-python`, `provides-extra`, `provides-extras` Resolved 4 packages in [TIME] Added idna v3.6 diff --git a/docs/reference/settings.md b/docs/reference/settings.md index cc746b294..9249d47b5 100644 --- a/docs/reference/settings.md +++ b/docs/reference/settings.md @@ -1047,7 +1047,7 @@ standard, though only the following fields are respected: to all versions of the package. - (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`). - (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`). -- (Optional) `provides-extras`: The extras provided by the package. +- (Optional) `provides-extra`: The extras provided by the package. **Default value**: `[]` @@ -2428,7 +2428,7 @@ standard, though only the following fields are respected: to all versions of the package. - (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`). - (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`). -- (Optional) `provides-extras`: The extras provided by the package. +- (Optional) `provides-extra`: The extras provided by the package. **Default value**: `[]` diff --git a/uv.schema.json b/uv.schema.json index 627680ca3..221c630e2 100644 --- a/uv.schema.json +++ b/uv.schema.json @@ -174,7 +174,7 @@ ] }, "dependency-metadata": { - "description": "Pre-defined static metadata for dependencies of the project (direct or transitive). When\nprovided, enables the resolver to use the specified metadata instead of querying the\nregistry or building the relevant package from source.\n\nMetadata should be provided in adherence with the [Metadata 2.3](https://packaging.python.org/en/latest/specifications/core-metadata/)\nstandard, though only the following fields are respected:\n\n- `name`: The name of the package.\n- (Optional) `version`: The version of the package. If omitted, the metadata will be applied\n to all versions of the package.\n- (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`).\n- (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`).\n- (Optional) `provides-extras`: The extras provided by the package.", + "description": "Pre-defined static metadata for dependencies of the project (direct or transitive). When\nprovided, enables the resolver to use the specified metadata instead of querying the\nregistry or building the relevant package from source.\n\nMetadata should be provided in adherence with the [Metadata 2.3](https://packaging.python.org/en/latest/specifications/core-metadata/)\nstandard, though only the following fields are respected:\n\n- `name`: The name of the package.\n- (Optional) `version`: The version of the package. If omitted, the metadata will be applied\n to all versions of the package.\n- (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`).\n- (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`).\n- (Optional) `provides-extra`: The extras provided by the package.", "type": [ "array", "null" @@ -1302,7 +1302,7 @@ ] }, "dependency-metadata": { - "description": "Pre-defined static metadata for dependencies of the project (direct or transitive). When\nprovided, enables the resolver to use the specified metadata instead of querying the\nregistry or building the relevant package from source.\n\nMetadata should be provided in adherence with the [Metadata 2.3](https://packaging.python.org/en/latest/specifications/core-metadata/)\nstandard, though only the following fields are respected:\n\n- `name`: The name of the package.\n- (Optional) `version`: The version of the package. If omitted, the metadata will be applied\n to all versions of the package.\n- (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`).\n- (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`).\n- (Optional) `provides-extras`: The extras provided by the package.", + "description": "Pre-defined static metadata for dependencies of the project (direct or transitive). When\nprovided, enables the resolver to use the specified metadata instead of querying the\nregistry or building the relevant package from source.\n\nMetadata should be provided in adherence with the [Metadata 2.3](https://packaging.python.org/en/latest/specifications/core-metadata/)\nstandard, though only the following fields are respected:\n\n- `name`: The name of the package.\n- (Optional) `version`: The version of the package. If omitted, the metadata will be applied\n to all versions of the package.\n- (Optional) `requires-dist`: The dependencies of the package (e.g., `werkzeug>=0.14`).\n- (Optional) `requires-python`: The Python version required by the package (e.g., `>=3.10`).\n- (Optional) `provides-extra`: The extras provided by the package.", "type": [ "array", "null" @@ -2195,7 +2195,7 @@ "name": { "$ref": "#/definitions/PackageName" }, - "provides-extras": { + "provides-extra": { "type": "array", "default": [], "items": {