-
Notifications
You must be signed in to change notification settings - Fork 2.5k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
1e48b75
commit 659a526
Showing
5 changed files
with
186 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,116 @@ | ||
use cargo::core::dependency::DepKind; | ||
use cargo::ops::cargo_remove::remove; | ||
use cargo::ops::cargo_remove::RemoveOptions; | ||
use cargo::ops::resolve_ws; | ||
use cargo::util::command_prelude::*; | ||
use cargo::util::toml_mut::manifest::DepTable; | ||
|
||
pub fn cli() -> clap::Command<'static> { | ||
clap::Command::new("remove") | ||
.setting(clap::AppSettings::DeriveDisplayOrder) | ||
.about("Remove dependencies from a Cargo.toml manifest file") | ||
.args([clap::Arg::new("dependencies") | ||
.action(clap::ArgAction::Append) | ||
.required(true) | ||
.multiple_values(true) | ||
.takes_value(true) | ||
.value_name("DEP_ID") | ||
.help("Dependencies to be removed")]) | ||
.arg_package("Package to remove from") | ||
.arg_manifest_path() | ||
.arg_quiet() | ||
.arg_dry_run("Don't actually write the manifest") | ||
.next_help_heading("SECTION") | ||
.args([ | ||
clap::Arg::new("dev") | ||
.long("dev") | ||
.conflicts_with("build") | ||
.action(clap::ArgAction::SetTrue) | ||
.group("section") | ||
.help("Remove as development dependency"), | ||
clap::Arg::new("build") | ||
.long("build") | ||
.conflicts_with("dev") | ||
.action(clap::ArgAction::SetTrue) | ||
.group("section") | ||
.help("Remove as build dependency"), | ||
clap::Arg::new("target") | ||
.long("target") | ||
.takes_value(true) | ||
.value_name("TARGET") | ||
.value_parser(clap::builder::NonEmptyStringValueParser::new()) | ||
.help("Remove as dependency from the given target platform"), | ||
]) | ||
} | ||
|
||
pub fn exec(config: &mut Config, args: &ArgMatches) -> CliResult { | ||
let dry_run = args.dry_run(); | ||
|
||
let workspace = args.workspace(config)?; | ||
let packages = args.packages_from_flags()?; | ||
let packages = packages.get_packages(&workspace)?; | ||
let spec = match packages.len() { | ||
0 => { | ||
return Err(CliError::new( | ||
anyhow::format_err!("no packages selected. Please specify one with `-p <PKG_ID>`"), | ||
101, | ||
)); | ||
} | ||
1 => packages[0], | ||
len => { | ||
return Err(CliError::new( | ||
anyhow::format_err!( | ||
"{len} packages selected. Please specify one with `-p <PKG_ID>`", | ||
), | ||
101, | ||
)); | ||
} | ||
}; | ||
|
||
let dependencies = args | ||
.get_many::<String>("dependencies") | ||
.expect("required(true)") | ||
.cloned() | ||
.collect(); | ||
|
||
let section = parse_section(args); | ||
|
||
let options = RemoveOptions { | ||
config, | ||
spec, | ||
dependencies, | ||
section, | ||
dry_run, | ||
}; | ||
remove(&options)?; | ||
|
||
if !dry_run { | ||
// Reload the workspace since we've changed dependencies | ||
let ws = args.workspace(config)?; | ||
resolve_ws(&ws)?; | ||
} | ||
|
||
Ok(()) | ||
} | ||
|
||
fn parse_section(args: &ArgMatches) -> DepTable { | ||
let dev = args.flag("dev"); | ||
let build = args.flag("build"); | ||
|
||
let kind = if dev { | ||
DepKind::Development | ||
} else if build { | ||
DepKind::Build | ||
} else { | ||
DepKind::Normal | ||
}; | ||
|
||
let mut table = DepTable::new().set_kind(kind); | ||
|
||
if let Some(target) = args.get_one::<String>("target") { | ||
assert!(!target.is_empty(), "Target specification may not be empty"); | ||
table = table.set_target(target); | ||
} | ||
|
||
table | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
//! Core of cargo-remove command | ||
use crate::core::Package; | ||
use crate::util::toml_mut::manifest::DepTable; | ||
use crate::util::toml_mut::manifest::LocalManifest; | ||
use crate::CargoResult; | ||
use crate::Config; | ||
|
||
/// Remove a dependency from a Cargo.toml manifest file. | ||
#[derive(Debug)] | ||
pub struct RemoveOptions<'a> { | ||
/// Configuration information for Cargo operations | ||
pub config: &'a Config, | ||
/// Package to remove dependencies from | ||
pub spec: &'a Package, | ||
/// Dependencies to remove | ||
pub dependencies: Vec<String>, | ||
/// Which dependency section to remove these from | ||
pub section: DepTable, | ||
/// Whether or not to actually write the manifest | ||
pub dry_run: bool, | ||
} | ||
|
||
/// Remove dependencies from a manifest | ||
pub fn remove(options: &RemoveOptions<'_>) -> CargoResult<()> { | ||
let dep_table = options | ||
.section | ||
.to_table() | ||
.into_iter() | ||
.map(String::from) | ||
.collect::<Vec<_>>(); | ||
|
||
let manifest_path = options.spec.manifest_path().to_path_buf(); | ||
let mut manifest = LocalManifest::try_new(&manifest_path)?; | ||
|
||
for dep in &options.dependencies { | ||
let section = if dep_table.len() >= 3 { | ||
format!("{} for target `{}`", &dep_table[2], &dep_table[1]) | ||
} else { | ||
dep_table[0].clone() | ||
}; | ||
options | ||
.config | ||
.shell() | ||
.status("Removing", format!("{dep} from {section}"))?; | ||
|
||
manifest.remove_from_table(&dep_table, dep)?; | ||
|
||
// Now that we have removed the crate, if that was the last reference to that | ||
// crate, then we need to drop any explicitly activated features on | ||
// that crate. | ||
manifest.gc_dep(dep); | ||
} | ||
|
||
if options.dry_run { | ||
options | ||
.config | ||
.shell() | ||
.warn("aborting remove due to dry run")?; | ||
} else { | ||
manifest.write()?; | ||
} | ||
|
||
Ok(()) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters