diff --git a/crates/uv/src/commands/mod.rs b/crates/uv/src/commands/mod.rs index c7154862f..24882ad10 100644 --- a/crates/uv/src/commands/mod.rs +++ b/crates/uv/src/commands/mod.rs @@ -36,9 +36,12 @@ pub(crate) use tool::run::run as tool_run; pub(crate) use tool::uninstall::uninstall as tool_uninstall; use uv_cache::Cache; use uv_fs::Simplified; +use uv_git::GitResolver; use uv_installer::compile_tree; use uv_normalize::PackageName; use uv_python::PythonEnvironment; +use uv_resolver::InMemoryIndex; +use uv_types::InFlight; pub(crate) use venv::venv; pub(crate) use version::version; @@ -167,3 +170,14 @@ pub(super) fn human_readable_bytes(bytes: u64) -> (f32, &'static str) { let i = ((bytes.log2() / 10.0) as usize).min(UNITS.len() - 1); (bytes / 1024_f32.powi(i as i32), UNITS[i]) } + +/// Shared state used during resolution and installation. +#[derive(Default)] +pub(crate) struct SharedState { + /// The resolved Git references. + pub(crate) git: GitResolver, + /// The fetched package versions and metadata. + pub(crate) index: InMemoryIndex, + /// The downloaded distributions. + pub(crate) in_flight: InFlight, +} diff --git a/crates/uv/src/commands/pip/install.rs b/crates/uv/src/commands/pip/install.rs index 0bb33142f..e1d2deaaa 100644 --- a/crates/uv/src/commands/pip/install.rs +++ b/crates/uv/src/commands/pip/install.rs @@ -18,21 +18,20 @@ use uv_configuration::{ use uv_configuration::{KeyringProviderType, TargetTriple}; use uv_dispatch::BuildDispatch; use uv_fs::Simplified; -use uv_git::GitResolver; use uv_installer::{SatisfiesResult, SitePackages}; use uv_python::{ EnvironmentPreference, Prefix, PythonEnvironment, PythonRequest, PythonVersion, Target, }; use uv_requirements::{RequirementsSource, RequirementsSpecification}; use uv_resolver::{ - DependencyMode, ExcludeNewer, FlatIndex, InMemoryIndex, OptionsBuilder, PreReleaseMode, - PythonRequirement, ResolutionMode, + DependencyMode, ExcludeNewer, FlatIndex, OptionsBuilder, PreReleaseMode, PythonRequirement, + ResolutionMode, }; -use uv_types::{BuildIsolation, HashStrategy, InFlight}; +use uv_types::{BuildIsolation, HashStrategy}; use crate::commands::pip::operations::Modifications; use crate::commands::pip::{operations, resolution_environment}; -use crate::commands::{elapsed, ExitStatus}; +use crate::commands::{elapsed, ExitStatus, SharedState}; use crate::printer::Printer; /// Install packages into the current environment. @@ -243,7 +242,6 @@ pub(crate) async fn pip_install( // When resolving, don't take any external preferences into account. let preferences = Vec::default(); - let git = GitResolver::default(); // Ignore development dependencies. let dev = Vec::default(); @@ -285,11 +283,8 @@ pub(crate) async fn pip_install( BuildIsolation::Isolated }; - // Create a shared in-memory index. - let index = InMemoryIndex::default(); - - // Track in-flight downloads, builds, etc., across resolutions. - let in_flight = InFlight::default(); + // Initialize any shared state. + let state = SharedState::default(); // Create a build dispatch. let build_dispatch = BuildDispatch::new( @@ -298,9 +293,9 @@ pub(crate) async fn pip_install( interpreter, &index_locations, &flat_index, - &index, - &git, - &in_flight, + &state.index, + &state.git, + &state.in_flight, index_strategy, setup_py, config_settings, @@ -339,7 +334,7 @@ pub(crate) async fn pip_install( python_requirement, &client, &flat_index, - &index, + &state.index, &build_dispatch, concurrency, options, @@ -371,7 +366,7 @@ pub(crate) async fn pip_install( &hasher, &tags, &client, - &in_flight, + &state.in_flight, concurrency, &build_dispatch, &cache, diff --git a/crates/uv/src/commands/pip/sync.rs b/crates/uv/src/commands/pip/sync.rs index d2bd34c5b..0c04490e5 100644 --- a/crates/uv/src/commands/pip/sync.rs +++ b/crates/uv/src/commands/pip/sync.rs @@ -17,21 +17,20 @@ use uv_configuration::{ use uv_configuration::{KeyringProviderType, TargetTriple}; use uv_dispatch::BuildDispatch; use uv_fs::Simplified; -use uv_git::GitResolver; use uv_installer::SitePackages; use uv_python::{ EnvironmentPreference, Prefix, PythonEnvironment, PythonRequest, PythonVersion, Target, }; use uv_requirements::{RequirementsSource, RequirementsSpecification}; use uv_resolver::{ - DependencyMode, ExcludeNewer, FlatIndex, InMemoryIndex, OptionsBuilder, PreReleaseMode, - PythonRequirement, ResolutionMode, + DependencyMode, ExcludeNewer, FlatIndex, OptionsBuilder, PreReleaseMode, PythonRequirement, + ResolutionMode, }; -use uv_types::{BuildIsolation, HashStrategy, InFlight}; +use uv_types::{BuildIsolation, HashStrategy}; use crate::commands::pip::operations::Modifications; use crate::commands::pip::{operations, resolution_environment}; -use crate::commands::ExitStatus; +use crate::commands::{ExitStatus, SharedState}; use crate::printer::Printer; /// Install a set of locked requirements into the current Python environment. @@ -231,15 +230,11 @@ pub(crate) async fn pip_sync( BuildIsolation::Isolated }; - // Create a shared in-memory index. - let index = InMemoryIndex::default(); - - // Track in-flight downloads, builds, etc., across resolutions. - let in_flight = InFlight::default(); + // Initialize any shared state. + let state = SharedState::default(); // When resolving, don't take any external preferences into account. let preferences = Vec::default(); - let git = GitResolver::default(); // Ignore development dependencies. let dev = Vec::default(); @@ -251,9 +246,9 @@ pub(crate) async fn pip_sync( interpreter, &index_locations, &flat_index, - &index, - &git, - &in_flight, + &state.index, + &state.git, + &state.in_flight, index_strategy, setup_py, config_settings, @@ -294,7 +289,7 @@ pub(crate) async fn pip_sync( python_requirement, &client, &flat_index, - &index, + &state.index, &build_dispatch, concurrency, options, @@ -326,7 +321,7 @@ pub(crate) async fn pip_sync( &hasher, &tags, &client, - &in_flight, + &state.in_flight, concurrency, &build_dispatch, &cache, diff --git a/crates/uv/src/commands/project/add.rs b/crates/uv/src/commands/project/add.rs index f410cff95..5700c97ce 100644 --- a/crates/uv/src/commands/project/add.rs +++ b/crates/uv/src/commands/project/add.rs @@ -8,19 +8,17 @@ use uv_dispatch::BuildDispatch; use uv_distribution::pyproject::{DependencyType, Source, SourceError}; use uv_distribution::pyproject_mut::PyProjectTomlMut; use uv_distribution::{DistributionDatabase, ProjectWorkspace, VirtualProject, Workspace}; -use uv_git::GitResolver; use uv_normalize::PackageName; use uv_python::{PythonFetch, PythonPreference, PythonRequest}; use uv_requirements::{NamedRequirementsResolver, RequirementsSource, RequirementsSpecification}; -use uv_resolver::{FlatIndex, InMemoryIndex}; -use uv_types::{BuildIsolation, HashStrategy, InFlight}; +use uv_resolver::FlatIndex; +use uv_types::{BuildIsolation, HashStrategy}; use uv_warnings::warn_user_once; use crate::commands::pip::operations::Modifications; use crate::commands::pip::resolution_environment; -use crate::commands::project::SharedState; use crate::commands::reporters::ResolverReporter; -use crate::commands::{project, ExitStatus}; +use crate::commands::{project, ExitStatus, SharedState}; use crate::printer::Printer; use crate::settings::ResolverInstallerSettings; @@ -107,9 +105,7 @@ pub(crate) async fn add( .build(); // Initialize any shared state. - let git = GitResolver::default(); - let in_flight = InFlight::default(); - let index = InMemoryIndex::default(); + let state = SharedState::default(); // Resolve the flat indexes from `--find-links`. let flat_index = { @@ -125,9 +121,9 @@ pub(crate) async fn add( venv.interpreter(), &settings.index_locations, &flat_index, - &index, - &git, - &in_flight, + &state.index, + &state.git, + &state.in_flight, settings.index_strategy, setup_py, &settings.config_setting, @@ -143,7 +139,7 @@ pub(crate) async fn add( let requirements = NamedRequirementsResolver::new( requirements, &hasher, - &index, + &state.index, DistributionDatabase::new(&client, &build_dispatch, concurrency.downloads, preview), ) .with_reporter(ResolverReporter::from(printer)) diff --git a/crates/uv/src/commands/project/lock.rs b/crates/uv/src/commands/project/lock.rs index c6718d2b2..f6f4e3b66 100644 --- a/crates/uv/src/commands/project/lock.rs +++ b/crates/uv/src/commands/project/lock.rs @@ -10,7 +10,7 @@ use uv_git::ResolvedRepositoryReference; use uv_python::{Interpreter, PythonFetch, PythonPreference, PythonRequest}; use uv_requirements::upgrade::{read_lockfile, LockedRequirements}; use uv_resolver::{FlatIndex, Lock, OptionsBuilder, PythonRequirement, RequiresPython}; -use uv_types::{BuildIsolation, EmptyInstalledPackages, HashStrategy, InFlight}; +use uv_types::{BuildIsolation, EmptyInstalledPackages, HashStrategy}; use uv_warnings::{warn_user, warn_user_once}; use crate::commands::project::{find_requires_python, FoundInterpreter, ProjectError, SharedState}; @@ -161,9 +161,6 @@ pub(super) async fn do_lock( .build(); let hasher = HashStrategy::Generate; - // Initialize any shared state. - let in_flight = InFlight::default(); - // TODO(charlie): These are all default values. We should consider whether we want to make them // optional on the downstream APIs. let build_isolation = BuildIsolation::default(); @@ -194,7 +191,7 @@ pub(super) async fn do_lock( &flat_index, &state.index, &state.git, - &in_flight, + &state.in_flight, index_strategy, setup_py, config_setting, diff --git a/crates/uv/src/commands/project/mod.rs b/crates/uv/src/commands/project/mod.rs index 3582a5ae6..bc538100b 100644 --- a/crates/uv/src/commands/project/mod.rs +++ b/crates/uv/src/commands/project/mod.rs @@ -13,19 +13,18 @@ use uv_configuration::{Concurrency, ExtrasSpecification, PreviewMode, SetupPyStr use uv_dispatch::BuildDispatch; use uv_distribution::{DistributionDatabase, Workspace}; use uv_fs::Simplified; -use uv_git::GitResolver; use uv_installer::{SatisfiesResult, SitePackages}; use uv_python::{ request_from_version_file, EnvironmentPreference, Interpreter, PythonEnvironment, PythonFetch, PythonInstallation, PythonPreference, PythonRequest, VersionRequest, }; use uv_requirements::{NamedRequirementsResolver, RequirementsSpecification}; -use uv_resolver::{FlatIndex, InMemoryIndex, OptionsBuilder, PythonRequirement, RequiresPython}; -use uv_types::{BuildIsolation, HashStrategy, InFlight}; +use uv_resolver::{FlatIndex, OptionsBuilder, PythonRequirement, RequiresPython}; +use uv_types::{BuildIsolation, HashStrategy}; -use crate::commands::pip; use crate::commands::pip::operations::Modifications; use crate::commands::reporters::ResolverReporter; +use crate::commands::{pip, SharedState}; use crate::printer::Printer; use crate::settings::ResolverInstallerSettings; @@ -278,15 +277,6 @@ pub(crate) async fn get_or_init_environment( } } -/// Shared state used during resolution and installation. -#[derive(Default)] -pub(crate) struct SharedState { - /// The resolved Git references. - git: GitResolver, - /// The fetched package versions and metadata. - index: InMemoryIndex, -} - /// Resolve any [`UnresolvedRequirementSpecification`] into a fully-qualified [`Requirement`]. pub(crate) async fn resolve_names( requirements: Vec, @@ -327,9 +317,6 @@ pub(crate) async fn resolve_names( .platform(interpreter.platform()) .build(); - // Initialize any shared state. - let in_flight = InFlight::default(); - // TODO(charlie): These are all default values. We should consider whether we want to make them // optional on the downstream APIs. let build_isolation = BuildIsolation::default(); @@ -346,7 +333,7 @@ pub(crate) async fn resolve_names( &flat_index, &state.index, &state.git, - &in_flight, + &state.in_flight, *index_strategy, setup_py, config_setting, @@ -448,9 +435,6 @@ pub(crate) async fn update_environment( .index_strategy(*index_strategy) .build(); - // Initialize any shared state. - let in_flight = InFlight::default(); - // TODO(charlie): These are all default values. We should consider whether we want to make them // optional on the downstream APIs. let build_isolation = BuildIsolation::default(); @@ -477,7 +461,7 @@ pub(crate) async fn update_environment( &flat_index, &state.index, &state.git, - &in_flight, + &state.in_flight, *index_strategy, setup_py, config_setting, @@ -534,7 +518,7 @@ pub(crate) async fn update_environment( &hasher, tags, &client, - &in_flight, + &state.in_flight, concurrency, &build_dispatch, cache, diff --git a/crates/uv/src/commands/project/remove.rs b/crates/uv/src/commands/project/remove.rs index 5730223ac..3a4cabaad 100644 --- a/crates/uv/src/commands/project/remove.rs +++ b/crates/uv/src/commands/project/remove.rs @@ -11,8 +11,7 @@ use uv_python::{PythonFetch, PythonPreference, PythonRequest}; use uv_warnings::{warn_user, warn_user_once}; use crate::commands::pip::operations::Modifications; -use crate::commands::project::SharedState; -use crate::commands::{project, ExitStatus}; +use crate::commands::{project, ExitStatus, SharedState}; use crate::printer::Printer; use crate::settings::{InstallerSettings, ResolverSettings}; diff --git a/crates/uv/src/commands/project/run.rs b/crates/uv/src/commands/project/run.rs index 4a3cc123f..2bc77bc6a 100644 --- a/crates/uv/src/commands/project/run.rs +++ b/crates/uv/src/commands/project/run.rs @@ -21,8 +21,7 @@ use uv_requirements::{RequirementsSource, RequirementsSpecification}; use uv_warnings::warn_user_once; use crate::commands::pip::operations::Modifications; -use crate::commands::project::SharedState; -use crate::commands::{project, ExitStatus}; +use crate::commands::{project, ExitStatus, SharedState}; use crate::printer::Printer; use crate::settings::ResolverInstallerSettings; diff --git a/crates/uv/src/commands/project/sync.rs b/crates/uv/src/commands/project/sync.rs index 42a352e44..9847cee59 100644 --- a/crates/uv/src/commands/project/sync.rs +++ b/crates/uv/src/commands/project/sync.rs @@ -8,7 +8,7 @@ use uv_distribution::{VirtualProject, DEV_DEPENDENCIES}; use uv_installer::SitePackages; use uv_python::{PythonEnvironment, PythonFetch, PythonPreference, PythonRequest}; use uv_resolver::{FlatIndex, Lock}; -use uv_types::{BuildIsolation, HashStrategy, InFlight}; +use uv_types::{BuildIsolation, HashStrategy}; use uv_warnings::warn_user_once; use crate::commands::pip::operations::Modifications; @@ -145,9 +145,6 @@ pub(super) async fn do_sync( .platform(venv.interpreter().platform()) .build(); - // Initialize any shared state. - let in_flight = InFlight::default(); - // TODO(charlie): These are all default values. We should consider whether we want to make them // optional on the downstream APIs. let build_isolation = BuildIsolation::default(); @@ -172,7 +169,7 @@ pub(super) async fn do_sync( &flat_index, &state.index, &state.git, - &in_flight, + &state.in_flight, index_strategy, setup_py, config_setting, @@ -199,7 +196,7 @@ pub(super) async fn do_sync( &hasher, tags, &client, - &in_flight, + &state.in_flight, concurrency, &build_dispatch, cache, diff --git a/crates/uv/src/commands/tool/install.rs b/crates/uv/src/commands/tool/install.rs index 3ee848a16..3dc937989 100644 --- a/crates/uv/src/commands/tool/install.rs +++ b/crates/uv/src/commands/tool/install.rs @@ -26,8 +26,8 @@ use uv_tool::{entrypoint_paths, find_executable_directory, InstalledTools, Tool, use uv_warnings::warn_user_once; use crate::commands::pip::operations::Modifications; -use crate::commands::project::{update_environment, SharedState}; -use crate::commands::{project, ExitStatus}; +use crate::commands::project::update_environment; +use crate::commands::{project, ExitStatus, SharedState}; use crate::printer::Printer; use crate::settings::ResolverInstallerSettings; diff --git a/crates/uv/src/commands/tool/run.rs b/crates/uv/src/commands/tool/run.rs index 70f678067..1b2054d0b 100644 --- a/crates/uv/src/commands/tool/run.rs +++ b/crates/uv/src/commands/tool/run.rs @@ -22,8 +22,8 @@ use uv_requirements::{RequirementsSource, RequirementsSpecification}; use uv_warnings::warn_user_once; use crate::commands::pip::operations::Modifications; -use crate::commands::project::{update_environment, SharedState}; -use crate::commands::ExitStatus; +use crate::commands::project::update_environment; +use crate::commands::{ExitStatus, SharedState}; use crate::printer::Printer; use crate::settings::ResolverInstallerSettings; diff --git a/crates/uv/src/commands/venv.rs b/crates/uv/src/commands/venv.rs index ee32d2da8..055d4134a 100644 --- a/crates/uv/src/commands/venv.rs +++ b/crates/uv/src/commands/venv.rs @@ -21,24 +21,19 @@ use uv_configuration::{ }; use uv_dispatch::BuildDispatch; use uv_fs::Simplified; -use uv_git::GitResolver; use uv_python::{ request_from_version_file, EnvironmentPreference, PythonFetch, PythonInstallation, PythonPreference, PythonRequest, }; -use uv_resolver::{ExcludeNewer, FlatIndex, InMemoryIndex}; -use uv_types::{BuildContext, BuildIsolation, HashStrategy, InFlight}; +use uv_resolver::{ExcludeNewer, FlatIndex}; +use uv_types::{BuildContext, BuildIsolation, HashStrategy}; -use crate::commands::{pip, ExitStatus}; +use crate::commands::{pip, ExitStatus, SharedState}; use crate::printer::Printer; use crate::shell::Shell; /// Create a virtual environment. -#[allow( - clippy::unnecessary_wraps, - clippy::too_many_arguments, - clippy::fn_params_excessive_bools -)] +#[allow(clippy::unnecessary_wraps, clippy::fn_params_excessive_bools)] pub(crate) async fn venv( path: &Path, python_request: Option<&str>, @@ -215,12 +210,8 @@ async fn venv_impl( ) }; - // Create a shared in-memory index. - let index = InMemoryIndex::default(); - let git = GitResolver::default(); - - // Track in-flight downloads, builds, etc., across resolutions. - let in_flight = InFlight::default(); + // Initialize any shared state. + let state = SharedState::default(); // For seed packages, assume the default settings and concurrency is sufficient. let config_settings = ConfigSettings::default(); @@ -236,9 +227,9 @@ async fn venv_impl( interpreter, index_locations, &flat_index, - &index, - &git, - &in_flight, + &state.index, + &state.git, + &state.in_flight, index_strategy, SetupPyStrategy::default(), &config_settings,