Skip to content

Commit 00873e2

Browse files
committed
Add support for uv python dir --bin (#8569)
Following #8458 we want to support showing the target directory in the CLI
1 parent 0793640 commit 00873e2

File tree

5 files changed

+79
-13
lines changed

5 files changed

+79
-13
lines changed

crates/uv-cli/src/lib.rs

+22-1
Original file line numberDiff line numberDiff line change
@@ -3836,7 +3836,9 @@ pub enum PythonCommand {
38363836
/// `%APPDATA%\uv\data\python` on Windows.
38373837
///
38383838
/// The Python installation directory may be overridden with `$UV_PYTHON_INSTALL_DIR`.
3839-
Dir,
3839+
///
3840+
/// To instead view the directory uv installs Python executables into, use the `--bin` flag.
3841+
Dir(PythonDirArgs),
38403842

38413843
/// Uninstall Python versions.
38423844
Uninstall(PythonUninstallArgs),
@@ -3864,6 +3866,25 @@ pub struct PythonListArgs {
38643866
pub only_installed: bool,
38653867
}
38663868

3869+
#[derive(Args)]
3870+
#[allow(clippy::struct_excessive_bools)]
3871+
pub struct PythonDirArgs {
3872+
/// Show the directory into which `uv python` will install Python executables.
3873+
///
3874+
/// By default, `uv python dir` shows the directory into which the Python distributions
3875+
/// themselves are installed, rather than the directory containing the linked executables.
3876+
///
3877+
/// The Python executable directory is determined according to the XDG standard and is derived
3878+
/// from the following environment variables, in order of preference:
3879+
///
3880+
/// - `$UV_PYTHON_BIN_DIR`
3881+
/// - `$XDG_BIN_HOME`
3882+
/// - `$XDG_DATA_HOME/../bin`
3883+
/// - `$HOME/.local/bin`
3884+
#[arg(long, verbatim_doc_comment)]
3885+
pub bin: bool,
3886+
}
3887+
38673888
#[derive(Args)]
38683889
#[allow(clippy::struct_excessive_bools)]
38693890
pub struct PythonInstallArgs {

crates/uv/src/commands/python/dir.rs

+15-9
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,21 @@ use anyhow::Context;
33
use owo_colors::OwoColorize;
44

55
use uv_fs::Simplified;
6-
use uv_python::managed::ManagedPythonInstallations;
6+
use uv_python::managed::{python_executable_dir, ManagedPythonInstallations};
7+
8+
/// Show the Python installation directory.
9+
pub(crate) fn dir(bin: bool) -> anyhow::Result<()> {
10+
if bin {
11+
let bin = python_executable_dir()?;
12+
println!("{}", bin.simplified_display().cyan());
13+
} else {
14+
let installed_toolchains = ManagedPythonInstallations::from_settings()
15+
.context("Failed to initialize toolchain settings")?;
16+
println!(
17+
"{}",
18+
installed_toolchains.root().simplified_display().cyan()
19+
);
20+
}
721

8-
/// Show the toolchain directory.
9-
pub(crate) fn dir() -> anyhow::Result<()> {
10-
let installed_toolchains = ManagedPythonInstallations::from_settings()
11-
.context("Failed to initialize toolchain settings")?;
12-
println!(
13-
"{}",
14-
installed_toolchains.root().simplified_display().cyan()
15-
);
1622
Ok(())
1723
}

crates/uv/src/lib.rs

+6-2
Original file line numberDiff line numberDiff line change
@@ -1118,9 +1118,13 @@ async fn run(mut cli: Cli) -> Result<ExitStatus> {
11181118
.await
11191119
}
11201120
Commands::Python(PythonNamespace {
1121-
command: PythonCommand::Dir,
1121+
command: PythonCommand::Dir(args),
11221122
}) => {
1123-
commands::python_dir()?;
1123+
// Resolve the settings from the command-line arguments and workspace configuration.
1124+
let args = settings::PythonDirSettings::resolve(args, filesystem);
1125+
show_settings!(args);
1126+
1127+
commands::python_dir(args.bin)?;
11241128
Ok(ExitStatus::Success)
11251129
}
11261130
Commands::Publish(args) => {

crates/uv/src/settings.rs

+18-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use url::Url;
88
use uv_cache::{CacheArgs, Refresh};
99
use uv_cli::{
1010
options::{flag, resolver_installer_options, resolver_options},
11-
AuthorFrom, BuildArgs, ExportArgs, PublishArgs, ToolUpgradeArgs,
11+
AuthorFrom, BuildArgs, ExportArgs, PublishArgs, PythonDirArgs, ToolUpgradeArgs,
1212
};
1313
use uv_cli::{
1414
AddArgs, ColorChoice, ExternalCommand, GlobalArgs, InitArgs, ListFormat, LockArgs, Maybe,
@@ -623,6 +623,23 @@ impl PythonListSettings {
623623
}
624624
}
625625

626+
/// The resolved settings to use for a `python dir` invocation.
627+
#[allow(clippy::struct_excessive_bools)]
628+
#[derive(Debug, Clone)]
629+
pub(crate) struct PythonDirSettings {
630+
pub(crate) bin: bool,
631+
}
632+
633+
impl PythonDirSettings {
634+
/// Resolve the [`PythonDirSettings`] from the CLI and filesystem configuration.
635+
#[allow(clippy::needless_pass_by_value)]
636+
pub(crate) fn resolve(args: PythonDirArgs, _filesystem: Option<FilesystemOptions>) -> Self {
637+
let PythonDirArgs { bin } = args;
638+
639+
Self { bin }
640+
}
641+
}
642+
626643
/// The resolved settings to use for a `python install` invocation.
627644
#[allow(clippy::struct_excessive_bools)]
628645
#[derive(Debug, Clone)]

docs/reference/cli.md

+18
Original file line numberDiff line numberDiff line change
@@ -4786,6 +4786,8 @@ By default, Python installations are stored in the uv data directory at `$XDG_DA
47864786

47874787
The Python installation directory may be overridden with `$UV_PYTHON_INSTALL_DIR`.
47884788

4789+
To instead view the directory uv installs Python executables into, use the `--bin` flag.
4790+
47894791
<h3 class="cli-reference">Usage</h3>
47904792

47914793
```
@@ -4803,6 +4805,22 @@ uv python dir [OPTIONS]
48034805
<p>WARNING: Hosts included in this list will not be verified against the system&#8217;s certificate store. Only use <code>--allow-insecure-host</code> in a secure network with verified sources, as it bypasses SSL verification and could expose you to MITM attacks.</p>
48044806

48054807
<p>May also be set with the <code>UV_INSECURE_HOST</code> environment variable.</p>
4808+
</dd><dt><code>--bin</code></dt><dd><p>Show the directory into which <code>uv python</code> will install Python executables.</p>
4809+
4810+
<p>By default, <code>uv python dir</code> shows the directory into which the Python distributions themselves are installed, rather than the directory containing the linked executables.</p>
4811+
4812+
<p>The Python executable directory is determined according to the XDG standard and is derived from the following environment variables, in order of preference:</p>
4813+
4814+
<ul>
4815+
<li><code>$UV_PYTHON_BIN_DIR</code></li>
4816+
4817+
<li><code>$XDG_BIN_HOME</code></li>
4818+
4819+
<li><code>$XDG_DATA_HOME/../bin</code></li>
4820+
4821+
<li><code>$HOME/.local/bin</code></li>
4822+
</ul>
4823+
48064824
</dd><dt><code>--cache-dir</code> <i>cache-dir</i></dt><dd><p>Path to the cache directory.</p>
48074825

48084826
<p>Defaults to <code>$XDG_CACHE_HOME/uv</code> or <code>$HOME/.cache/uv</code> on macOS and Linux, and <code>%LOCALAPPDATA%\uv\cache</code> on Windows.</p>

0 commit comments

Comments
 (0)