diff --git a/crates/uv-python/src/version_files.rs b/crates/uv-python/src/version_files.rs index 4067d1b4dd23..22cad953cd83 100644 --- a/crates/uv-python/src/version_files.rs +++ b/crates/uv-python/src/version_files.rs @@ -56,7 +56,17 @@ async fn read_versions_file() -> Result>, std::io::Error> { match fs::tokio::read_to_string(PYTHON_VERSIONS_FILENAME).await { Ok(content) => { debug!("Reading requests from `{PYTHON_VERSIONS_FILENAME}`"); - Ok(Some(content.lines().map(ToString::to_string).collect())) + Ok(Some( + content + .lines() + .filter(|line| { + // Skip comments and empty lines. + let trimmed = line.trim(); + !(trimmed.is_empty() || trimmed.starts_with('#')) + }) + .map(ToString::to_string) + .collect(), + )) } Err(err) if err.kind() == std::io::ErrorKind::NotFound => Ok(None), Err(err) => Err(err), @@ -67,7 +77,14 @@ async fn read_version_file() -> Result, std::io::Error> { match fs::tokio::read_to_string(PYTHON_VERSION_FILENAME).await { Ok(content) => { debug!("Reading requests from `{PYTHON_VERSION_FILENAME}`"); - Ok(content.lines().next().map(ToString::to_string)) + Ok(content + .lines() + .find(|line| { + // Skip comments and empty lines. + let trimmed = line.trim(); + !(trimmed.is_empty() || trimmed.starts_with('#')) + }) + .map(ToString::to_string)) } Err(err) if err.kind() == std::io::ErrorKind::NotFound => Ok(None), Err(err) => Err(err), diff --git a/crates/uv/tests/python_pin.rs b/crates/uv/tests/python_pin.rs index 53ca8fce7c80..416b8c388aa0 100644 --- a/crates/uv/tests/python_pin.rs +++ b/crates/uv/tests/python_pin.rs @@ -1,11 +1,12 @@ #![cfg(all(feature = "python", feature = "pypi"))] -use assert_fs::fixture::{FileWriteStr as _, PathChild as _}; +use anyhow::Result; +use assert_fs::fixture::{FileWriteStr, PathChild}; use common::{uv_snapshot, TestContext}; use insta::assert_snapshot; use uv_python::{ platform::{Arch, Os}, - PYTHON_VERSION_FILENAME, + PYTHON_VERSIONS_FILENAME, PYTHON_VERSION_FILENAME, }; mod common; @@ -629,3 +630,41 @@ fn python_pin_resolve() { "###); }); } + +#[test] +fn python_pin_with_comments() -> Result<()> { + let context = TestContext::new_with_versions(&[]); + + let content = indoc::indoc! {r" + 3.12 + + # 3.11 + 3.10 + "}; + + let version_file = context.temp_dir.child(PYTHON_VERSION_FILENAME); + version_file.write_str(content)?; + uv_snapshot!(context.filters(), context.python_pin(), @r###" + success: true + exit_code: 0 + ----- stdout ----- + 3.12 + + ----- stderr ----- + "###); + fs_err::remove_file(version_file)?; + + let versions_file = context.temp_dir.child(PYTHON_VERSIONS_FILENAME); + versions_file.write_str(content)?; + uv_snapshot!(context.filters(), context.python_pin(), @r###" + success: true + exit_code: 0 + ----- stdout ----- + 3.12 + 3.10 + + ----- stderr ----- + "###); + + Ok(()) +}