Add `uv add --no-sync` and `uv remove --no-sync` (#5881)

## Summary

Closes https://github.com/astral-sh/uv/issues/5867.
This commit is contained in:
Charlie Marsh 2024-08-07 14:09:10 -04:00 committed by GitHub
parent 9bb55c4ac0
commit 8c6b667eeb
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
6 changed files with 76 additions and 0 deletions

View File

@ -2304,6 +2304,10 @@ pub struct AddArgs {
#[arg(long)]
pub extra: Option<Vec<ExtraName>>,
/// Avoid syncing the virtual environment after re-locking the project.
#[arg(long, conflicts_with = "frozen")]
pub no_sync: bool,
/// Assert that the `uv.lock` will remain unchanged.
#[arg(long, conflicts_with = "frozen")]
pub locked: bool,
@ -2354,6 +2358,10 @@ pub struct RemoveArgs {
#[arg(long, conflicts_with("dev"))]
pub optional: Option<ExtraName>,
/// Avoid syncing the virtual environment after re-locking the project.
#[arg(long, conflicts_with = "frozen")]
pub no_sync: bool,
/// Assert that the `uv.lock` will remain unchanged.
#[arg(long, conflicts_with = "frozen")]
pub locked: bool,

View File

@ -37,6 +37,7 @@ use crate::settings::ResolverInstallerSettings;
pub(crate) async fn add(
locked: bool,
frozen: bool,
no_sync: bool,
requirements: Vec<RequirementsSource>,
editable: Option<bool>,
dependency_type: DependencyType,
@ -364,6 +365,10 @@ pub(crate) async fn add(
}
}
if no_sync {
return Ok(ExitStatus::Success);
}
// Sync the environment.
let (extras, dev) = match dependency_type {
DependencyType::Production => {

View File

@ -17,9 +17,11 @@ use crate::printer::Printer;
use crate::settings::ResolverInstallerSettings;
/// Remove one or more packages from the project requirements.
#[allow(clippy::fn_params_excessive_bools)]
pub(crate) async fn remove(
locked: bool,
frozen: bool,
no_sync: bool,
requirements: Vec<PackageName>,
dependency_type: DependencyType,
package: Option<PackageName>,
@ -120,6 +122,10 @@ pub(crate) async fn remove(
)
.await?;
if no_sync {
return Ok(ExitStatus::Success);
}
// Perform a full sync, because we don't know what exactly is affected by the removal.
// TODO(ibraheem): Should we accept CLI overrides for this? Should we even sync here?
let extras = ExtrasSpecification::All;

View File

@ -1068,6 +1068,7 @@ async fn run_project(
commands::add(
args.locked,
args.frozen,
args.no_sync,
args.requirements,
args.editable,
args.dependency_type,
@ -1103,6 +1104,7 @@ async fn run_project(
commands::remove(
args.locked,
args.frozen,
args.no_sync,
args.requirements,
args.dependency_type,
args.package,

View File

@ -639,6 +639,7 @@ impl LockSettings {
pub(crate) struct AddSettings {
pub(crate) locked: bool,
pub(crate) frozen: bool,
pub(crate) no_sync: bool,
pub(crate) requirements: Vec<RequirementsSource>,
pub(crate) dependency_type: DependencyType,
pub(crate) editable: Option<bool>,
@ -668,6 +669,7 @@ impl AddSettings {
rev,
tag,
branch,
no_sync,
locked,
frozen,
installer,
@ -693,6 +695,7 @@ impl AddSettings {
Self {
locked,
frozen,
no_sync,
requirements,
dependency_type,
raw_sources,
@ -718,6 +721,7 @@ impl AddSettings {
pub(crate) struct RemoveSettings {
pub(crate) locked: bool,
pub(crate) frozen: bool,
pub(crate) no_sync: bool,
pub(crate) requirements: Vec<PackageName>,
pub(crate) dependency_type: DependencyType,
pub(crate) package: Option<PackageName>,
@ -734,6 +738,7 @@ impl RemoveSettings {
dev,
optional,
requirements,
no_sync,
locked,
frozen,
installer,
@ -754,6 +759,7 @@ impl RemoveSettings {
Self {
locked,
frozen,
no_sync,
requirements,
dependency_type,
package,

View File

@ -2136,6 +2136,55 @@ fn add_frozen() -> Result<()> {
Ok(())
}
/// Add a requirement without updating the environment.
#[test]
fn add_no_sync() -> Result<()> {
let context = TestContext::new("3.12");
let pyproject_toml = context.temp_dir.child("pyproject.toml");
pyproject_toml.write_str(indoc! {r#"
[project]
name = "project"
version = "0.1.0"
# ...
requires-python = ">=3.12"
dependencies = []
"#})?;
uv_snapshot!(context.filters(), context.add(&["anyio==3.7.0"]).arg("--no-sync"), @r###"
success: true
exit_code: 0
----- stdout -----
----- stderr -----
warning: `uv add` is experimental and may change without warning
Resolved 4 packages in [TIME]
"###);
let pyproject_toml = fs_err::read_to_string(context.temp_dir.join("pyproject.toml"))?;
insta::with_settings!({
filters => context.filters(),
}, {
assert_snapshot!(
pyproject_toml, @r###"
[project]
name = "project"
version = "0.1.0"
# ...
requires-python = ">=3.12"
dependencies = [
"anyio==3.7.0",
]
"###
);
});
assert!(context.temp_dir.join("uv.lock").exists());
Ok(())
}
#[test]
fn add_reject_multiple_git_ref_flags() {
let context = TestContext::new("3.12");