Skip to content

Commit 323bf9f

Browse files
committed
cli: prepare DistOptions in advance
1 parent 97d2100 commit 323bf9f

File tree

8 files changed

+104
-129
lines changed

8 files changed

+104
-129
lines changed

src/cli/common.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,9 @@ use tracing_subscriber::{EnvFilter, Registry, reload::Handle};
1616

1717
use crate::{
1818
config::Cfg,
19-
dist::{TargetTriple, ToolchainDesc},
19+
dist::{DistOptions, TargetTriple, ToolchainDesc},
2020
errors::RustupError,
21-
install::UpdateStatus,
21+
install::{InstallMethod, UpdateStatus},
2222
process::Process,
2323
toolchain::{LocalToolchainName, Toolchain, ToolchainName},
2424
utils,
@@ -217,10 +217,10 @@ pub(crate) async fn update_all_channels(
217217
) -> Result<utils::ExitCode> {
218218
let profile = cfg.get_profile()?;
219219
let mut toolchains = Vec::new();
220-
for (desc, mut distributable) in cfg.list_channels()? {
221-
let result = distributable
222-
.update(&[], &[], profile, force_update, false)
223-
.await;
220+
for (desc, distributable) in cfg.list_channels()? {
221+
let options = DistOptions::new(&[], &[], &desc, profile, force_update, cfg)?
222+
.for_update(&distributable, false);
223+
let result = InstallMethod::Dist(options).install().await;
224224

225225
if let Err(e) = &result {
226226
error!("{e}");

src/cli/rustup_mode.rs

Lines changed: 15 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ use crate::{
4141
command, component_for_bin,
4242
config::{ActiveSource, Cfg},
4343
dist::{
44-
AutoInstallMode, PartialToolchainDesc, Profile, TargetTriple,
44+
AutoInstallMode, DistOptions, PartialToolchainDesc, Profile, TargetTriple,
4545
download::DownloadCfg,
4646
manifest::{Component, ComponentStatus},
4747
},
@@ -960,27 +960,23 @@ async fn update(
960960

961961
let components = opts.component.iter().map(|s| &**s).collect::<Vec<_>>();
962962
let targets = opts.target.iter().map(|s| &**s).collect::<Vec<_>>();
963+
let dist_opts = DistOptions::new(
964+
&components,
965+
&targets,
966+
&desc,
967+
cfg.get_profile()?,
968+
opts.force,
969+
cfg,
970+
)?;
963971

964-
let force = opts.force;
965-
let allow_downgrade = opts.allow_downgrade;
966-
let profile = cfg.get_profile()?;
967972
let status = match DistributableToolchain::new(cfg, desc.clone()) {
968-
Ok(mut d) => {
969-
let profile = cfg.get_profile()?;
970-
d.update(&components, &targets, profile, force, allow_downgrade)
973+
Ok(d) => {
974+
InstallMethod::Dist(dist_opts.for_update(&d, opts.allow_downgrade))
975+
.install()
971976
.await?
972977
}
973978
Err(RustupError::ToolchainNotInstalled { .. }) => {
974-
DistributableToolchain::install(
975-
cfg,
976-
&desc,
977-
&components,
978-
&targets,
979-
profile,
980-
force,
981-
)
982-
.await?
983-
.0
979+
DistributableToolchain::install(dist_opts).await?.0
984980
}
985981
Err(e) => Err(e)?,
986982
};
@@ -1520,10 +1516,8 @@ async fn override_add(
15201516
Err(e @ RustupError::ToolchainNotInstalled { .. }) => match &toolchain_name {
15211517
ToolchainName::Custom(_) => Err(e)?,
15221518
ToolchainName::Official(desc) => {
1523-
let status =
1524-
DistributableToolchain::install(cfg, desc, &[], &[], cfg.get_profile()?, false)
1525-
.await?
1526-
.0;
1519+
let options = DistOptions::new(&[], &[], desc, cfg.get_profile()?, false, cfg)?;
1520+
let status = DistributableToolchain::install(options).await?.0;
15271521
writeln!(cfg.process.stdout().lock())?;
15281522
common::show_channel_update(
15291523
cfg,

src/cli/self_update.rs

Lines changed: 10 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -59,10 +59,13 @@ use crate::{
5959
markdown::md,
6060
},
6161
config::Cfg,
62-
dist::{PartialToolchainDesc, Profile, TargetTriple, ToolchainDesc, download::DownloadCfg},
62+
dist::{
63+
DistOptions, PartialToolchainDesc, Profile, TargetTriple, ToolchainDesc,
64+
download::DownloadCfg,
65+
},
6366
download::download_file,
6467
errors::RustupError,
65-
install::UpdateStatus,
68+
install::{InstallMethod, UpdateStatus},
6669
process::Process,
6770
toolchain::{
6871
DistributableToolchain, MaybeOfficialToolchainName, ResolvableToolchainName, Toolchain,
@@ -996,28 +999,20 @@ async fn maybe_install_rust(opts: InstallOpts<'_>, cfg: &mut Cfg<'_>) -> Result<
996999
let (components, targets) = (opts.components, opts.targets);
9971000
let toolchain = opts.install(cfg)?;
9981001
if let Some(desc) = &toolchain {
1002+
let options = DistOptions::new(components, targets, desc, cfg.get_profile()?, true, cfg)?;
9991003
let status = if Toolchain::exists(cfg, &desc.into())? {
10001004
warn!("Updating existing toolchain, profile choice will be ignored");
10011005
// If we have a partial install we might not be able to read content here. We could:
10021006
// - fail and folk have to delete the partially present toolchain to recover
10031007
// - silently ignore it (and provide inconsistent metadata for reporting the install/update change)
10041008
// - delete the partial install and start over
10051009
// For now, we error.
1006-
let mut toolchain = DistributableToolchain::new(cfg, desc.clone())?;
1007-
toolchain
1008-
.update(components, targets, cfg.get_profile()?, true, false)
1010+
let toolchain = DistributableToolchain::new(cfg, desc.clone())?;
1011+
InstallMethod::Dist(options.for_update(&toolchain, false))
1012+
.install()
10091013
.await?
10101014
} else {
1011-
DistributableToolchain::install(
1012-
cfg,
1013-
desc,
1014-
components,
1015-
targets,
1016-
cfg.get_profile()?,
1017-
true,
1018-
)
1019-
.await?
1020-
.0
1015+
DistributableToolchain::install(options).await?.0
10211016
};
10221017

10231018
check_proxy_sanity(cfg.process, components, desc)?;

src/config.rs

Lines changed: 22 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,15 @@ use serde::Deserialize;
88
use thiserror::Error as ThisError;
99
use tracing::{debug, error, info, trace, warn};
1010

11-
use crate::dist::AutoInstallMode;
1211
use crate::{
1312
cli::{common, self_update::SelfUpdateMode},
14-
dist::{self, PartialToolchainDesc, Profile, TargetTriple, ToolchainDesc, temp},
13+
dist::{
14+
self, AutoInstallMode, DistOptions, PartialToolchainDesc, Profile, TargetTriple,
15+
ToolchainDesc, temp,
16+
},
1517
errors::RustupError,
1618
fallback_settings::FallbackSettings,
17-
install::UpdateStatus,
19+
install::{InstallMethod, UpdateStatus},
1820
process::Process,
1921
settings::{MetadataVersion, Settings, SettingsFile},
2022
toolchain::{
@@ -787,29 +789,30 @@ impl<'a> Cfg<'a> {
787789
}
788790
let components: Vec<_> = components.iter().map(AsRef::as_ref).collect();
789791
let targets: Vec<_> = targets.iter().map(AsRef::as_ref).collect();
790-
let profile = match profile {
791-
Some(profile) => profile,
792-
None => self.get_profile()?,
793-
};
792+
let mut options = DistOptions::new(
793+
&components,
794+
&targets,
795+
toolchain,
796+
match profile {
797+
Some(p) => p,
798+
None => self.get_profile()?,
799+
},
800+
false,
801+
self,
802+
)?;
803+
794804
let (status, toolchain) = match DistributableToolchain::new(self, toolchain.clone()) {
795805
Err(RustupError::ToolchainNotInstalled { .. }) => {
796-
DistributableToolchain::install(
797-
self,
798-
toolchain,
799-
&components,
800-
&targets,
801-
profile,
802-
false,
803-
)
804-
.await?
806+
DistributableToolchain::install(options).await?
805807
}
806-
Ok(mut distributable) => {
808+
Ok(distributable) => {
807809
if verbose {
808810
info!("using existing install for {toolchain}");
809811
}
810812
let status = if !distributable.components_exist(&components, &targets)? {
811-
distributable
812-
.update(&components, &targets, profile, true, false)
813+
options.force = true;
814+
InstallMethod::Dist(options.for_update(&distributable, false))
815+
.install()
813816
.await?
814817
} else {
815818
UpdateStatus::Unchanged

src/dist/mod.rs

Lines changed: 39 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,13 @@ use serde::{Deserialize, Serialize};
1919
use thiserror::Error as ThisError;
2020
use tracing::{debug, info, warn};
2121

22-
use crate::{config::Cfg, errors::RustupError, process::Process, toolchain::ToolchainName, utils};
22+
use crate::{
23+
config::Cfg,
24+
errors::RustupError,
25+
process::Process,
26+
toolchain::{DistributableToolchain, ToolchainName},
27+
utils,
28+
};
2329

2430
pub mod component;
2531
pub(crate) mod config;
@@ -876,14 +882,14 @@ impl fmt::Display for Profile {
876882
}
877883
}
878884

879-
pub(crate) struct DistOptions<'a> {
880-
pub(super) cfg: &'a Cfg<'a>,
885+
pub(crate) struct DistOptions<'cfg, 'a> {
886+
pub(super) cfg: &'cfg Cfg<'cfg>,
881887
pub(super) toolchain: &'a ToolchainDesc,
882888
profile: Profile,
883889
pub(super) update_hash: PathBuf,
884-
dl_cfg: DownloadCfg<'a>,
890+
dl_cfg: DownloadCfg<'cfg>,
885891
/// --force bool is whether to force an update/install
886-
force: bool,
892+
pub(super) force: bool,
887893
/// --allow-downgrade
888894
pub(super) allow_downgrade: bool,
889895
/// toolchain already exists
@@ -896,14 +902,14 @@ pub(crate) struct DistOptions<'a> {
896902
targets: &'a [&'a str],
897903
}
898904

899-
impl<'a> DistOptions<'a> {
905+
impl<'cfg, 'a> DistOptions<'cfg, 'a> {
900906
pub(super) fn new(
901907
components: &'a [&'a str],
902908
targets: &'a [&'a str],
903909
toolchain: &'a ToolchainDesc,
904910
profile: Profile,
905911
force: bool,
906-
cfg: &'a Cfg<'_>,
912+
cfg: &'cfg Cfg<'cfg>,
907913
) -> Result<Self> {
908914
Ok(Self {
909915
cfg,
@@ -919,6 +925,31 @@ impl<'a> DistOptions<'a> {
919925
targets,
920926
})
921927
}
928+
929+
pub(super) fn for_update(
930+
mut self,
931+
toolchain: &'a DistributableToolchain<'cfg>,
932+
allow_downgrade: bool,
933+
) -> Self {
934+
self.allow_downgrade = allow_downgrade;
935+
self.exists = true;
936+
self.old_date_version =
937+
// Ignore a missing manifest: we can't report the old version
938+
// correctly, and it probably indicates an incomplete install, so do
939+
// not report an old rustc version either.
940+
toolchain.get_manifest()
941+
.map(|m| {
942+
(
943+
m.date,
944+
// should rustc_version be a free function on a trait?
945+
// note that prev_version can be junk if the rustc component is missing ...
946+
toolchain.toolchain.rustc_version(),
947+
)
948+
})
949+
.ok();
950+
951+
self
952+
}
922953
}
923954

924955
// Installs or updates a toolchain from a dist server. If an initial
@@ -929,7 +960,7 @@ impl<'a> DistOptions<'a> {
929960
#[tracing::instrument(level = "trace", err(level = "trace"), skip_all, fields(profile = ?opts.profile, prefix = %prefix.path().display()))]
930961
pub(crate) async fn update_from_dist(
931962
prefix: &InstallPrefix,
932-
opts: &DistOptions<'_>,
963+
opts: &DistOptions<'_, '_>,
933964
) -> Result<Option<String>> {
934965
let fresh_install = !prefix.path().exists();
935966
// fresh_install means the toolchain isn't present, but hash_exists means there is a stray hash file

src/install.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,21 +20,21 @@ pub(crate) enum UpdateStatus {
2020
Unchanged,
2121
}
2222

23-
pub(crate) enum InstallMethod<'a> {
23+
pub(crate) enum InstallMethod<'cfg, 'a> {
2424
Copy {
2525
src: &'a Path,
2626
dest: &'a CustomToolchainName,
27-
cfg: &'a Cfg<'a>,
27+
cfg: &'cfg Cfg<'cfg>,
2828
},
2929
Link {
3030
src: &'a Path,
3131
dest: &'a CustomToolchainName,
32-
cfg: &'a Cfg<'a>,
32+
cfg: &'cfg Cfg<'cfg>,
3333
},
34-
Dist(DistOptions<'a>),
34+
Dist(DistOptions<'cfg, 'a>),
3535
}
3636

37-
impl InstallMethod<'_> {
37+
impl InstallMethod<'_, '_> {
3838
// Install a toolchain
3939
#[tracing::instrument(level = "trace", err(level = "trace"), skip_all)]
4040
pub(crate) async fn install(self) -> Result<UpdateStatus> {

src/toolchain.rs

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ use crate::{
2323
RustupError,
2424
config::{ActiveSource, Cfg, InstalledPath},
2525
dist::{
26-
PartialToolchainDesc, TargetTriple,
26+
DistOptions, PartialToolchainDesc, TargetTriple,
2727
component::{Component, Components},
2828
prefix::InstallPrefix,
2929
},
@@ -61,12 +61,8 @@ impl<'a> Toolchain<'a> {
6161
name: ToolchainName::Official(desc),
6262
..
6363
}) if install_if_missing => {
64-
Ok(
65-
DistributableToolchain::install(cfg, &desc, &[], &[], cfg.get_profile()?, true)
66-
.await?
67-
.1
68-
.toolchain,
69-
)
64+
let options = DistOptions::new(&[], &[], &desc, cfg.get_profile()?, true, cfg)?;
65+
Ok(DistributableToolchain::install(options).await?.1.toolchain)
7066
}
7167
Err(e) => Err(e.into()),
7268
}

0 commit comments

Comments
 (0)