use std::str::FromStr;
use std::sync::Arc;
use clap::Parser;
use miette::IntoDiagnostic;
use rattler_conda_types::{Channel, ChannelConfig, MatchSpec, Platform};
use rattler_networking::AuthenticationMiddleware;
use crate::repodata::fetch_sparse_repodata;
use super::{install::globally_install_package, list::list_global_packages};
#[derive(Parser, Debug)]
#[clap(arg_required_else_help = true)]
pub struct Args {
package: String,
#[clap(short, long, default_values = ["conda-forge"])]
channel: Vec<String>,
}
pub async fn execute(args: Args) -> miette::Result<()> {
let package = args.package;
let channel_config = ChannelConfig::default();
let channels = args
.channel
.iter()
.map(|c| Channel::from_str(c, &channel_config))
.collect::<Result<Vec<Channel>, _>>()
.into_diagnostic()?;
let package_matchspec = MatchSpec::from_str(&package).into_diagnostic()?;
if !list_global_packages()
.await?
.iter()
.any(|global_package| global_package.as_source() == package)
{
miette::bail!(
"{} package is not globally installed",
console::style("!").yellow().bold()
);
}
let authenticated_client = reqwest_middleware::ClientBuilder::new(reqwest::Client::new())
.with_arc(Arc::new(AuthenticationMiddleware::default()))
.build();
let platform_sparse_repodata =
fetch_sparse_repodata(&channels, [Platform::current()], &authenticated_client).await?;
let (package_record, _, upgraded) = globally_install_package(
package_matchspec,
&platform_sparse_repodata,
&channel_config,
authenticated_client,
)
.await?;
let package_record = package_record.repodata_record.package_record;
if upgraded {
eprintln!(
"Updated package {} to version {}",
package_record.name.as_normalized(),
package_record.version
);
} else {
eprintln!(
"Package {} is already up-to-date",
package_record.name.as_normalized(),
);
}
Ok(())
}