Skip to content

Commit e290094

Browse files
Copilotj178
andauthored
Skip invalid Rust toolchains instead of failing (#1699)
If any rustup toolchain has a broken `rustc` binary (e.g. a partially-built stage0 sysroot registered via rustup), `prek` would fail entirely when trying to select a suitable toolchain, even if many valid toolchains were available. Closes #1695 ## Changes - **`rustup.rs`**: In both `list_installed_toolchains()` and `list_system_toolchains()`, replace `try_collect()` with `filter_map()` so that toolchains whose `rustc --version` fails are skipped with a `warn!` log rather than propagating the error. The overall operation succeeds as long as at least one valid toolchain exists. ```rust // Before: one failure poisons the entire stream .try_collect() .await? // After: bad toolchains are warned and skipped .filter_map(async move |result| match result { Ok(info) => Some(info), Err(e) => { warn!("Skipping invalid toolchain: {e:#}"); None } }) .collect() .await ``` <!-- START COPILOT ORIGINAL PROMPT --> <details> <summary>Original prompt</summary> ---- *This section details on the original issue you should resolve* <issue_title>One invalid Rust toolchain causes prek to fail</issue_title> <issue_description>### Summary When running a Rust-based hook, I've got the following error: ``` error: Failed to install hook `oxipng` caused by: Failed to install rust caused by: Failed to read version from /home/m4tx/projects/rust/build/host/stage0-sysroot/bin/rustc caused by: Run command `rustc version` failed caused by: No such file or directory (os error 2) ``` This was very concerning for me at first, since `/home/m4tx/projects` is a very arbitrary path that I happen to store various repositories in, and I would never expect prek to look for anything in there. Running prek with `-vvv` did shine some light on this: ``` 2026-02-26T16:45:23.963699Z TRACE Executing `/home/m4tx/.rustup/toolchains/nightly-2025-07-03-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.963942Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.42.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.964608Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.57.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.964848Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.60-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.965053Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.64.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.965181Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.70.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.965471Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.75.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.966651Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.77.2-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.972872Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.78.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.975137Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.79.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.977357Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.80.1-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.977749Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.81.0-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.977995Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.84.1-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.978252Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.85-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.978423Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.85.1-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.978681Z TRACE Executing `/home/m4tx/.rustup/toolchains/1.93-x86_64-unknown-linux-gnu/bin/rustc --version` 2026-02-26T16:45:23.983378Z TRACE Executing `/home/m4tx/projects/rust/build/host/stage0-sysroot/bin/rustc --version` ``` Turns out that I was trying to compile Rust from scratch, which resulted in the toolchain being added to `rustup`. For the next 6 months ran into any issues because of this (since I had a number of other perfectly working toolchains installed) until I tried prek. Removing the problematic toolchain from rustup has fixed the problem. I don't think that `prek` should fail on _any_ when it encounters failure using any toolchain; rather, I would expect it to work if at least one Rust toolchain is usable. ### Willing to submit a PR? - [x] Yes — I’m willing to open a PR to fix this. ### Platform Arch Linux, Linux 6.12.74-1-lts x86_64 GNU/Linux ### Version prek 0.3.3 ### .pre-commit-config.yaml ```yaml repos: - repo: https://github.com/oxipng/oxipng rev: v9.1.4 hooks: - id: oxipng args: ["-o", "max", "--strip", "safe", "--alpha"] ``` ### Log file ``` 2026-02-26T16:45:23.937725Z DEBUG prek: 0.3.3 2026-02-26T16:45:23.937755Z DEBUG Args: ["prek", "-vvv"] 2026-02-26T16:45:23.938885Z TRACE get_root: close time.busy=1.10ms time.idle=2.87µs 2026-02-26T16:45:23.938914Z DEBUG Git root: /home/m4tx/projects/m4txblog 2026-02-26T16:45:23.938928Z TRACE Executing `/usr/bin/git ls-files --unmerged` 2026-02-26T16:45:23.939978Z DEBUG Found workspace root at `/home/m4tx/projects/m4txblog` 2026-02-26T16:45:23.939988Z TRACE Include selectors: `` 2026-02-26T16:45:23.939993Z TRACE Skip selectors: `` 2026-02-26T16:45:23.940045Z DEBUG discover{root="/home/m4tx/projects/m4txblog" config=None refresh=false}: Loaded workspace from cache 2026-02-26T16:45:23.940061Z DEBUG discover{root="/home/m4tx/projects/m4txblog" config=None refresh=false}: Loading project configuration path=.pre-commit-config.yaml 2026-02-26T16:45:23.940757Z TRACE discover{root="/home/m4tx/projects/m4txblog" config=None refresh=false}: close time.busy=748µs time.idle=1.18µs 2026-02-26T16:45:23.940780Z TRACE Executing `/usr/bin/git diff --exit-code --name-only -z /home/m4tx/projects/m4txblog/.pre-commit-config.yaml` 2026-02-26T1... </details> <!-- START COPILOT CODING AGENT SUFFIX --> - Fixes #1695 <!-- START COPILOT CODING AGENT TIPS --> --- 🔒 GitHub Advanced Security automatically protects Copilot coding agent pull requests. You can protect all pull requests by enabling Advanced Security for your repositories. [Learn more about Advanced Security.](https://gh.io/cca-advanced-security) --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: j178 <10510431+j178@users.noreply.github.com>
1 parent a64312f commit e290094

File tree

1 file changed

+20
-6
lines changed

1 file changed

+20
-6
lines changed

crates/prek/src/languages/rust/rustup.rs

Lines changed: 20 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,11 @@ use std::path::{Path, PathBuf};
33
use std::sync::LazyLock;
44

55
use anyhow::{Context, Result};
6-
use futures::{StreamExt, TryStreamExt};
6+
use futures::StreamExt;
77
use prek_consts::env_vars::EnvVars;
88
use semver::Version;
99
use target_lexicon::HOST;
10-
use tracing::{debug, trace};
10+
use tracing::{debug, trace, warn};
1111

1212
use crate::fs::LockedFile;
1313
use crate::languages::REQWEST_CLIENT;
@@ -182,8 +182,15 @@ impl Rustup {
182182
let infos: Vec<ToolchainInfo> = futures::stream::iter(entries)
183183
.map(async move |(name, path)| toolchain_info(name, path).await)
184184
.buffer_unordered(8)
185-
.try_collect()
186-
.await?;
185+
.filter_map(async move |result| match result {
186+
Ok(info) => Some(info),
187+
Err(e) => {
188+
warn!("Skipping invalid toolchain: {e:#}");
189+
None
190+
}
191+
})
192+
.collect()
193+
.await;
187194

188195
Ok(infos)
189196
}
@@ -208,8 +215,15 @@ impl Rustup {
208215
let infos: Vec<ToolchainInfo> = futures::stream::iter(entries)
209216
.map(async move |(name, path)| toolchain_info(name, path).await)
210217
.buffer_unordered(8)
211-
.try_collect()
212-
.await?;
218+
.filter_map(async move |result| match result {
219+
Ok(info) => Some(info),
220+
Err(e) => {
221+
warn!("Skipping invalid toolchain: {e:#}");
222+
None
223+
}
224+
})
225+
.collect()
226+
.await;
213227

214228
Ok(infos)
215229
}

0 commit comments

Comments
 (0)