mirror of https://github.com/astral-sh/uv
Avoid rejecting already-installed URL distributions with `--no-sources` (#16094)
## Summary This PR removes a guard that was accidentally included in https://github.com/astral-sh/uv/pull/15234/files#diff-6be6d80fe4821c47b70a372260f55e73b8da8182b8dcad7525d5cd3eb584532b. I meant to remove that logic before merging. Closes https://github.com/astral-sh/uv/issues/16068.
This commit is contained in:
parent
0bd3dfd5ea
commit
8da9df3654
|
|
@ -6,10 +6,8 @@ use pubgrub::Range;
|
||||||
use smallvec::SmallVec;
|
use smallvec::SmallVec;
|
||||||
use tracing::{debug, trace};
|
use tracing::{debug, trace};
|
||||||
|
|
||||||
use uv_configuration::{IndexStrategy, SourceStrategy};
|
use uv_configuration::IndexStrategy;
|
||||||
use uv_distribution_types::{
|
use uv_distribution_types::{CompatibleDist, IncompatibleDist, IncompatibleSource, IndexUrl};
|
||||||
CompatibleDist, IncompatibleDist, IncompatibleSource, IndexUrl, InstalledDistKind,
|
|
||||||
};
|
|
||||||
use uv_distribution_types::{DistributionMetadata, IncompatibleWheel, Name, PrioritizedDist};
|
use uv_distribution_types::{DistributionMetadata, IncompatibleWheel, Name, PrioritizedDist};
|
||||||
use uv_normalize::PackageName;
|
use uv_normalize::PackageName;
|
||||||
use uv_pep440::Version;
|
use uv_pep440::Version;
|
||||||
|
|
@ -28,7 +26,6 @@ pub(crate) struct CandidateSelector {
|
||||||
resolution_strategy: ResolutionStrategy,
|
resolution_strategy: ResolutionStrategy,
|
||||||
prerelease_strategy: PrereleaseStrategy,
|
prerelease_strategy: PrereleaseStrategy,
|
||||||
index_strategy: IndexStrategy,
|
index_strategy: IndexStrategy,
|
||||||
source_strategy: SourceStrategy,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl CandidateSelector {
|
impl CandidateSelector {
|
||||||
|
|
@ -37,7 +34,6 @@ impl CandidateSelector {
|
||||||
options: &Options,
|
options: &Options,
|
||||||
manifest: &Manifest,
|
manifest: &Manifest,
|
||||||
env: &ResolverEnvironment,
|
env: &ResolverEnvironment,
|
||||||
source_strategy: SourceStrategy,
|
|
||||||
) -> Self {
|
) -> Self {
|
||||||
Self {
|
Self {
|
||||||
resolution_strategy: ResolutionStrategy::from_mode(
|
resolution_strategy: ResolutionStrategy::from_mode(
|
||||||
|
|
@ -53,7 +49,6 @@ impl CandidateSelector {
|
||||||
options.dependency_mode,
|
options.dependency_mode,
|
||||||
),
|
),
|
||||||
index_strategy: options.index_strategy,
|
index_strategy: options.index_strategy,
|
||||||
source_strategy,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -124,13 +119,7 @@ impl CandidateSelector {
|
||||||
let installed = if reinstall {
|
let installed = if reinstall {
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
Self::get_installed(
|
Self::get_installed(package_name, range, installed_packages, tags)
|
||||||
package_name,
|
|
||||||
range,
|
|
||||||
installed_packages,
|
|
||||||
tags,
|
|
||||||
self.source_strategy,
|
|
||||||
)
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// If we're not upgrading, we should prefer the already-installed distribution.
|
// If we're not upgrading, we should prefer the already-installed distribution.
|
||||||
|
|
@ -380,7 +369,6 @@ impl CandidateSelector {
|
||||||
range: &Range<Version>,
|
range: &Range<Version>,
|
||||||
installed_packages: &'a InstalledPackages,
|
installed_packages: &'a InstalledPackages,
|
||||||
tags: Option<&'a Tags>,
|
tags: Option<&'a Tags>,
|
||||||
source_strategy: SourceStrategy,
|
|
||||||
) -> Option<Candidate<'a>> {
|
) -> Option<Candidate<'a>> {
|
||||||
let installed_dists = installed_packages.get_packages(package_name);
|
let installed_dists = installed_packages.get_packages(package_name);
|
||||||
match installed_dists.as_slice() {
|
match installed_dists.as_slice() {
|
||||||
|
|
@ -393,16 +381,6 @@ impl CandidateSelector {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
|
|
||||||
// When sources are disabled, only allow registry installations to be reused
|
|
||||||
if matches!(source_strategy, SourceStrategy::Disabled) {
|
|
||||||
if !matches!(dist.kind, InstalledDistKind::Registry(_)) {
|
|
||||||
debug!(
|
|
||||||
"Source strategy is disabled, rejecting non-registry installed distribution: {dist}"
|
|
||||||
);
|
|
||||||
return None;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Verify that the installed distribution is compatible with the environment.
|
// Verify that the installed distribution is compatible with the environment.
|
||||||
if tags.is_some_and(|tags| {
|
if tags.is_some_and(|tags| {
|
||||||
let Ok(Some(wheel_tags)) = dist.read_tags() else {
|
let Ok(Some(wheel_tags)) = dist.read_tags() else {
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,7 @@ use tokio::sync::oneshot;
|
||||||
use tokio_stream::wrappers::ReceiverStream;
|
use tokio_stream::wrappers::ReceiverStream;
|
||||||
use tracing::{Level, debug, info, instrument, trace, warn};
|
use tracing::{Level, debug, info, instrument, trace, warn};
|
||||||
|
|
||||||
use uv_configuration::{Constraints, Overrides, SourceStrategy};
|
use uv_configuration::{Constraints, Overrides};
|
||||||
use uv_distribution::{ArchiveMetadata, DistributionDatabase};
|
use uv_distribution::{ArchiveMetadata, DistributionDatabase};
|
||||||
use uv_distribution_types::{
|
use uv_distribution_types::{
|
||||||
BuiltDist, CompatibleDist, DerivationChain, Dist, DistErrorKind, DistributionMetadata,
|
BuiltDist, CompatibleDist, DerivationChain, Dist, DistErrorKind, DistributionMetadata,
|
||||||
|
|
@ -201,7 +201,6 @@ impl<'a, Context: BuildContext, InstalledPackages: InstalledPackagesProvider>
|
||||||
build_context.git(),
|
build_context.git(),
|
||||||
build_context.capabilities(),
|
build_context.capabilities(),
|
||||||
build_context.locations(),
|
build_context.locations(),
|
||||||
build_context.sources(),
|
|
||||||
provider,
|
provider,
|
||||||
installed_packages,
|
installed_packages,
|
||||||
)
|
)
|
||||||
|
|
@ -225,7 +224,6 @@ impl<Provider: ResolverProvider, InstalledPackages: InstalledPackagesProvider>
|
||||||
git: &GitResolver,
|
git: &GitResolver,
|
||||||
capabilities: &IndexCapabilities,
|
capabilities: &IndexCapabilities,
|
||||||
locations: &IndexLocations,
|
locations: &IndexLocations,
|
||||||
source_strategy: SourceStrategy,
|
|
||||||
provider: Provider,
|
provider: Provider,
|
||||||
installed_packages: InstalledPackages,
|
installed_packages: InstalledPackages,
|
||||||
) -> Result<Self, ResolveError> {
|
) -> Result<Self, ResolveError> {
|
||||||
|
|
@ -233,7 +231,7 @@ impl<Provider: ResolverProvider, InstalledPackages: InstalledPackagesProvider>
|
||||||
index: index.clone(),
|
index: index.clone(),
|
||||||
git: git.clone(),
|
git: git.clone(),
|
||||||
capabilities: capabilities.clone(),
|
capabilities: capabilities.clone(),
|
||||||
selector: CandidateSelector::for_resolution(&options, &manifest, &env, source_strategy),
|
selector: CandidateSelector::for_resolution(&options, &manifest, &env),
|
||||||
dependency_mode: options.dependency_mode,
|
dependency_mode: options.dependency_mode,
|
||||||
urls: Urls::from_manifest(&manifest, &env, git, options.dependency_mode),
|
urls: Urls::from_manifest(&manifest, &env, git, options.dependency_mode),
|
||||||
indexes: Indexes::from_manifest(&manifest, &env, options.dependency_mode),
|
indexes: Indexes::from_manifest(&manifest, &env, options.dependency_mode),
|
||||||
|
|
|
||||||
|
|
@ -12358,6 +12358,87 @@ fn reject_invalid_short_usize_zip64() {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Regression test for: <https://github.com/astral-sh/uv/issues/16068>
|
||||||
|
#[test]
|
||||||
|
fn already_installed_url_dependency_no_sources() -> Result<()> {
|
||||||
|
let context = TestContext::new("3.12").with_filtered_counts();
|
||||||
|
|
||||||
|
context
|
||||||
|
.temp_dir
|
||||||
|
.child("foo")
|
||||||
|
.child("pyproject.toml")
|
||||||
|
.write_str(indoc! {r#"
|
||||||
|
[project]
|
||||||
|
name = "foo"
|
||||||
|
version = "0.1.0"
|
||||||
|
requires-python = ">=3.12"
|
||||||
|
dependencies = ["iniconfig"]
|
||||||
|
|
||||||
|
[build-system]
|
||||||
|
requires = ["hatchling"]
|
||||||
|
build-backend = "hatchling.build"
|
||||||
|
"#})?;
|
||||||
|
context
|
||||||
|
.temp_dir
|
||||||
|
.child("foo")
|
||||||
|
.child("src")
|
||||||
|
.child("foo")
|
||||||
|
.child("__init__.py")
|
||||||
|
.touch()?;
|
||||||
|
|
||||||
|
context
|
||||||
|
.temp_dir
|
||||||
|
.child("bar")
|
||||||
|
.child("pyproject.toml")
|
||||||
|
.write_str(indoc! {r#"
|
||||||
|
[project]
|
||||||
|
name = "bar"
|
||||||
|
version = "0.1.0"
|
||||||
|
requires-python = ">=3.12"
|
||||||
|
dependencies = ["foo"]
|
||||||
|
|
||||||
|
[build-system]
|
||||||
|
requires = ["hatchling"]
|
||||||
|
build-backend = "hatchling.build"
|
||||||
|
"#})?;
|
||||||
|
context
|
||||||
|
.temp_dir
|
||||||
|
.child("bar")
|
||||||
|
.child("src")
|
||||||
|
.child("bar")
|
||||||
|
.child("__init__.py")
|
||||||
|
.touch()?;
|
||||||
|
|
||||||
|
// Install `foo`.
|
||||||
|
uv_snapshot!(context.filters(), context.pip_install().arg("./foo"), @r"
|
||||||
|
success: true
|
||||||
|
exit_code: 0
|
||||||
|
----- stdout -----
|
||||||
|
|
||||||
|
----- stderr -----
|
||||||
|
Resolved [N] packages in [TIME]
|
||||||
|
Prepared [N] packages in [TIME]
|
||||||
|
Installed [N] packages in [TIME]
|
||||||
|
+ foo==0.1.0 (from file://[TEMP_DIR]/foo)
|
||||||
|
+ iniconfig==2.0.0
|
||||||
|
");
|
||||||
|
|
||||||
|
// Install `bar` with `--no-sources`.
|
||||||
|
uv_snapshot!(context.filters(), context.pip_install().arg("./bar").arg("--no-sources"), @r"
|
||||||
|
success: true
|
||||||
|
exit_code: 0
|
||||||
|
----- stdout -----
|
||||||
|
|
||||||
|
----- stderr -----
|
||||||
|
Resolved [N] packages in [TIME]
|
||||||
|
Prepared [N] packages in [TIME]
|
||||||
|
Installed [N] packages in [TIME]
|
||||||
|
+ bar==0.1.0 (from file://[TEMP_DIR]/bar)
|
||||||
|
");
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
/// Test that build dependencies respect locked versions from the resolution.
|
/// Test that build dependencies respect locked versions from the resolution.
|
||||||
#[test]
|
#[test]
|
||||||
fn pip_install_build_dependencies_respect_locked_versions() -> Result<()> {
|
fn pip_install_build_dependencies_respect_locked_versions() -> Result<()> {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue