Skip to content

Commit 3bfcd63

Browse files
authored
fix: project platform remove (#3017)
1 parent 1013a8f commit 3bfcd63

File tree

3 files changed

+42
-32
lines changed

3 files changed

+42
-32
lines changed

crates/pixi_manifest/src/manifests/manifest.rs

Lines changed: 23 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -352,35 +352,41 @@ impl Manifest {
352352
/// Remove the platform(s) from the project
353353
pub fn remove_platforms(
354354
&mut self,
355-
platforms: impl IntoIterator<Item = Platform>,
355+
platforms: impl IntoIterator<Item = Platform> + Clone,
356356
feature_name: &FeatureName,
357357
) -> miette::Result<()> {
358-
// Get current platforms and platform to remove for the feature
358+
// Get current platforms for the feature
359359
let current = match feature_name {
360360
FeatureName::Default => self.workspace.workspace.platforms.get_mut(),
361361
FeatureName::Named(_) => self.feature_mut(feature_name)?.platforms_mut(),
362362
};
363-
// Get the platforms to remove, while checking if they exist
364-
let to_remove: IndexSet<_> = platforms
365-
.into_iter()
366-
.map(|c| {
367-
current
368-
.iter()
369-
.position(|x| *x == c)
370-
.ok_or_else(|| miette::miette!("platform {} does not exist", c))
371-
.map(|_| c)
372-
})
373-
.collect::<Result<_, _>>()?;
374363

375-
let retained: IndexSet<_> = current.difference(&to_remove).cloned().collect();
364+
// Check if some platforms are not part of current
365+
let missing = platforms
366+
.clone()
367+
.into_iter()
368+
.filter(|p| !current.contains(p))
369+
.collect_vec();
370+
if !missing.is_empty() {
371+
return Err(miette::miette!(
372+
"The following platform{} are not part of {}: {}",
373+
if missing.len() > 1 { "s are" } else { " is" },
374+
feature_name,
375+
missing.into_iter().join(", ")
376+
));
377+
}
376378

377379
// Remove platforms from the manifest
378-
current.retain(|p| retained.contains(p));
380+
current.retain(|p| !platforms.clone().into_iter().contains(p));
379381

380382
// And from the TOML document
381-
let retained = retained.iter().map(|p| p.to_string()).collect_vec();
383+
let retained = current.iter().map(|p| p.to_string()).collect_vec();
382384
let platforms = self.source.get_array_mut("platforms", feature_name)?;
383-
platforms.retain(|x| retained.contains(&x.to_string()));
385+
platforms.retain(|p| {
386+
p.as_str()
387+
.map(|p| retained.contains(&p.to_string()))
388+
.unwrap_or(false)
389+
});
384390

385391
Ok(())
386392
}

src/cli/project/platform/remove.rs

Lines changed: 3 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,17 @@
1-
use std::str::FromStr;
2-
31
use crate::lock_file::UpdateMode;
42
use crate::{
53
environment::{get_update_lock_file_and_prefix, LockFileUsage},
64
Project, UpdateLockFileOptions,
75
};
86
use clap::Parser;
9-
use miette::IntoDiagnostic;
107
use pixi_manifest::FeatureName;
118
use rattler_conda_types::Platform;
129

1310
#[derive(Parser, Debug, Default)]
1411
pub struct Args {
1512
/// The platform name(s) to remove.
1613
#[clap(required = true, num_args=1..)]
17-
pub platform: Vec<String>,
14+
pub platforms: Vec<Platform>,
1815

1916
/// Don't update the environment, only remove the platform(s) from the
2017
/// lock-file.
@@ -31,18 +28,10 @@ pub async fn execute(mut project: Project, args: Args) -> miette::Result<()> {
3128
.feature
3229
.map_or(FeatureName::Default, FeatureName::Named);
3330

34-
// Determine which platforms to remove
35-
let platforms = args
36-
.platform
37-
.into_iter()
38-
.map(|platform_str| Platform::from_str(&platform_str))
39-
.collect::<Result<Vec<_>, _>>()
40-
.into_diagnostic()?;
41-
4231
// Remove the platform(s) from the manifest
4332
project
4433
.manifest
45-
.remove_platforms(platforms.clone(), &feature_name)?;
34+
.remove_platforms(args.platforms.clone(), &feature_name)?;
4635

4736
get_update_lock_file_and_prefix(
4837
&project.default_environment(),
@@ -57,7 +46,7 @@ pub async fn execute(mut project: Project, args: Args) -> miette::Result<()> {
5746
project.save()?;
5847

5948
// Report back to the user
60-
for platform in platforms {
49+
for platform in args.platforms {
6150
eprintln!(
6251
"{}Removed {}",
6352
console::style(console::Emoji("✔ ", "")).green(),

tests/integration_python/test_main_cli.py

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,13 +116,14 @@ def test_project_commands(pixi: Path, tmp_pixi_workspace: Path) -> None:
116116
"platform",
117117
"add",
118118
"linux-64",
119+
"osx-arm64",
119120
],
120121
ExitCode.SUCCESS,
121122
)
122123
verify_cli_command(
123124
[pixi, "project", "--manifest-path", manifest_path, "platform", "list"],
124125
ExitCode.SUCCESS,
125-
stdout_contains="linux-64",
126+
stdout_contains=["linux-64", "osx-arm64"],
126127
)
127128
verify_cli_command(
128129
[
@@ -136,9 +137,23 @@ def test_project_commands(pixi: Path, tmp_pixi_workspace: Path) -> None:
136137
],
137138
ExitCode.SUCCESS,
138139
)
140+
verify_cli_command(
141+
[
142+
pixi,
143+
"project",
144+
"--manifest-path",
145+
manifest_path,
146+
"platform",
147+
"remove",
148+
"linux-64",
149+
],
150+
ExitCode.FAILURE,
151+
stderr_contains="linux-64",
152+
)
139153
verify_cli_command(
140154
[pixi, "project", "--manifest-path", manifest_path, "platform", "list"],
141155
ExitCode.SUCCESS,
156+
stdout_contains="osx-arm64",
142157
stdout_excludes="linux-64",
143158
)
144159

0 commit comments

Comments
 (0)