Skip to content

Commit bd87c3a

Browse files
feat(downloads): introduce RUSTUP_CONCURRENT_DOWNLOADS to control concurrency
1 parent 3d99833 commit bd87c3a

File tree

4 files changed

+21
-4
lines changed

4 files changed

+21
-4
lines changed

doc/user-guide/src/environment-variables.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,9 @@
6969
- `RUSTUP_DOWNLOAD_TIMEOUT` *unstable* (default: 180). Allows to override the default
7070
timeout (in seconds) for downloading components.
7171

72+
- `RUSTUP_CONCURRENT_DOWNLOADS` *unstable* (default: the number of components to download). Controls the number of
73+
downloads made concurrently.
74+
7275
[directive syntax]: https://docs.rs/tracing-subscriber/latest/tracing_subscriber/filter/struct.EnvFilter.html#directives
7376
[dc]: https://docs.docker.com/storage/storagedriver/overlayfs-driver/#modifying-files-or-directories
7477
[override]: overrides.md

src/cli/rustup_mode.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -799,7 +799,8 @@ async fn check_updates(cfg: &Cfg<'_>, opts: CheckOpts) -> Result<utils::ExitCode
799799
let use_colors = matches!(t.color_choice(), ColorChoice::Auto | ColorChoice::Always);
800800
let mut update_available = false;
801801
let channels = cfg.list_channels()?;
802-
let num_channels = channels.len();
802+
let num_channels = cfg.process.concurrent_downloads().unwrap_or(channels.len());
803+
803804
// Ensure that `.buffered()` is never called with 0 as this will cause a hang.
804805
// See: https://github.com/rust-lang/futures-rs/pull/1194#discussion_r209501774
805806
if num_channels > 0 {

src/dist/manifestation.rs

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -154,7 +154,10 @@ impl Manifestation {
154154
let mut things_to_install: Vec<(Component, CompressionKind, File)> = Vec::new();
155155
let mut things_downloaded: Vec<String> = Vec::new();
156156
let components = update.components_urls_and_hashes(new_manifest)?;
157-
let components_len = components.len();
157+
let num_channels = download_cfg
158+
.process
159+
.concurrent_downloads()
160+
.unwrap_or(components.len());
158161

159162
const DEFAULT_MAX_RETRIES: usize = 3;
160163
let max_retries: usize = download_cfg
@@ -188,9 +191,9 @@ impl Manifestation {
188191
new_manifest,
189192
)
190193
});
191-
if components_len > 0 {
194+
if num_channels > 0 {
192195
let results = component_stream
193-
.buffered(components_len)
196+
.buffered(num_channels)
194197
.collect::<Vec<_>>()
195198
.await;
196199
for result in results {

src/process.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ use std::ffi::OsString;
22
use std::fmt::Debug;
33
use std::io;
44
use std::io::IsTerminal;
5+
use std::num::NonZeroU64;
56
use std::path::PathBuf;
67
use std::str::FromStr;
78
#[cfg(feature = "test")]
@@ -167,6 +168,15 @@ impl Process {
167168
_ => ProgressDrawTarget::hidden(),
168169
}
169170
}
171+
172+
pub fn concurrent_downloads(&self) -> Option<usize> {
173+
match self.var("RUSTUP_CONCURRENT_DOWNLOADS") {
174+
Ok(s) => Some(NonZeroU64::from_str(&s).context(
175+
"invalid value in RUSTUP_CONCURRENT_DOWNLOADS -- must be a natural number greater than zero"
176+
).ok()?.get() as usize),
177+
Err(_) => None,
178+
}
179+
}
170180
}
171181

172182
impl home::env::Env for Process {

0 commit comments

Comments
 (0)