From 1bb9aa68f2cc2bc6127c0871fdabe6b144ddb909 Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Thu, 13 Aug 2026 07:17:12 +0000 Subject: [PATCH 1/2] fix(pwsh): stop empty Invoke-Expression on profile init PowerShell's pyenv wrapper used console passthrough for init, so a second `iex ((pyenv init - pwsh)...)` (duplicate profile lines or re-init) captured nothing and failed on PS 7.6. Pipeline-capture init/virtualenv-init, guard empty iex in profile snippets, skip duplicate installer blocks, bump 0.2.36. Co-authored-by: I'm Your Boy Roy --- Cargo.lock | 8 ++--- Cargo.toml | 2 +- crates/pyenv-core/src/doctor/helpers.rs | 2 +- crates/pyenv-core/src/meta/compat_docs.rs | 2 +- .../pyenv-core/src/meta/public_docs/system.rs | 2 +- crates/pyenv-core/src/shell/emit/functions.rs | 22 +++++++++--- crates/pyenv-core/src/shell/init.rs | 3 +- crates/pyenv-core/src/shell/tests.rs | 35 +++++++++++++++++++ crates/pyenv-gui/src/main.rs | 2 +- crates/pyenv-gui/tauri.conf.json | 2 +- docs/CLI.md | 3 +- docs/INSTRUCTIONS.md | 3 +- python-package/pyproject.toml | 2 +- .../src/pyenv_native_bootstrap/__init__.py | 2 +- scripts/install-pyenv-native.ps1 | 8 ++++- scripts/smoke-shells.ps1 | 15 ++++++-- 16 files changed, 91 insertions(+), 22 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index e000b98..e79783e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2692,7 +2692,7 @@ dependencies = [ [[package]] name = "pyenv-cli" -version = "0.2.35" +version = "0.2.36" dependencies = [ "anyhow", "clap", @@ -2701,7 +2701,7 @@ dependencies = [ [[package]] name = "pyenv-core" -version = "0.2.35" +version = "0.2.36" dependencies = [ "anyhow", "bzip2", @@ -2719,7 +2719,7 @@ dependencies = [ [[package]] name = "pyenv-gui" -version = "0.2.35" +version = "0.2.36" dependencies = [ "pyenv-core", "rfd", @@ -2732,7 +2732,7 @@ dependencies = [ [[package]] name = "pyenv-mcp" -version = "0.2.35" +version = "0.2.36" dependencies = [ "anyhow", "clap", diff --git a/Cargo.toml b/Cargo.toml index 2f807d2..be747a8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,4 +8,4 @@ resolver = "2" [workspace.package] edition = "2024" license = "MIT" -version = "0.2.35" \ No newline at end of file +version = "0.2.36" \ No newline at end of file diff --git a/crates/pyenv-core/src/doctor/helpers.rs b/crates/pyenv-core/src/doctor/helpers.rs index dfbe0cb..a3790e8 100644 --- a/crates/pyenv-core/src/doctor/helpers.rs +++ b/crates/pyenv-core/src/doctor/helpers.rs @@ -13,7 +13,7 @@ pub(super) fn shell_init_hint(ctx: &AppContext, platform: &str) -> String { Some("cmd") => { "Add `for /f \"delims=\" %i in ('pyenv init - cmd') do %i` to your shell startup or rerun the Windows installer".to_string() } - _ => "Add `iex ((pyenv init - pwsh) -join \"`n\")` to your PowerShell profile or rerun the Windows installer".to_string(), + _ => "Add `$__pyenv_init = (pyenv init - pwsh) -join \"`n\"; if ($__pyenv_init) { Invoke-Expression $__pyenv_init }` to your PowerShell profile or rerun the Windows installer".to_string(), }, _ => match ctx.env_shell.as_deref() { Some("zsh") => "Add `eval \"$(pyenv init - zsh)\"` to ~/.zshrc".to_string(), diff --git a/crates/pyenv-core/src/meta/compat_docs.rs b/crates/pyenv-core/src/meta/compat_docs.rs index a210004..23a1c23 100644 --- a/crates/pyenv-core/src/meta/compat_docs.rs +++ b/crates/pyenv-core/src/meta/compat_docs.rs @@ -126,7 +126,7 @@ pub(super) const COMPATIBILITY_COMMAND_DOCS: &[CommandDoc] = &[ "", "Examples:", " eval \"$(pyenv virtualenv-init - bash)\"", - " iex ((pyenv virtualenv-init - pwsh) -join \"`n\")", + " $__pyenv_init = (pyenv virtualenv-init - pwsh) -join \"`n\"; if ($__pyenv_init) { Invoke-Expression $__pyenv_init }", "", "Preferred native command: `pyenv init - `.", ], diff --git a/crates/pyenv-core/src/meta/public_docs/system.rs b/crates/pyenv-core/src/meta/public_docs/system.rs index 1f76e9d..b5064c8 100644 --- a/crates/pyenv-core/src/meta/public_docs/system.rs +++ b/crates/pyenv-core/src/meta/public_docs/system.rs @@ -77,7 +77,7 @@ pub(super) const SYSTEM_COMMAND_DOCS: &[CommandDoc] = &[ "Supported shells: pwsh (PowerShell), cmd, bash, zsh, fish, sh", "", "Setup (add to your shell profile):", - " PowerShell: iex ((pyenv init - pwsh) -join \"`n\")", + " PowerShell: $__pyenv_init = (pyenv init - pwsh) -join \"`n\"; if ($__pyenv_init) { Invoke-Expression $__pyenv_init }", " Bash: eval \"$(pyenv init - bash)\"", " Zsh: eval \"$(pyenv init - zsh)\"", " Fish: pyenv init - fish | source", diff --git a/crates/pyenv-core/src/shell/emit/functions.rs b/crates/pyenv-core/src/shell/emit/functions.rs index abeb49b..56eba0b 100644 --- a/crates/pyenv-core/src/shell/emit/functions.rs +++ b/crates/pyenv-core/src/shell/emit/functions.rs @@ -79,6 +79,12 @@ fn render_pwsh_shell_function(exe_path: &str) -> Vec { " $global:LASTEXITCODE = $process.ExitCode".to_string(), " return $process.ExitCode".to_string(), "}".to_string(), + "function Invoke-PyenvExpression {".to_string(), + " param([string[]]$ShellCmds)".to_string(), + " if ($null -eq $ShellCmds -or $ShellCmds.Count -eq 0) { return }".to_string(), + " $expr = (($ShellCmds | Where-Object { $null -ne $_ }) -join \"`n\").Trim()".to_string(), + " if ($expr.Length -gt 0) { Invoke-Expression $expr }".to_string(), + "}".to_string(), "function pyenv {".to_string(), format!(" $pyenvExe = '{}'", ps_single_quote(exe_path)), " if ($args.Count -eq 0) {".to_string(), @@ -90,19 +96,27 @@ fn render_pwsh_shell_function(exe_path: &str) -> Vec { " switch ($command) {".to_string(), " 'shell' {".to_string(), " $shellCmds = Invoke-PyenvCaptured $pyenvExe (@('sh-shell', '--') + @($arguments))".to_string(), - " if ($LASTEXITCODE -eq 0 -and $shellCmds.Count -gt 0) { Invoke-Expression ($shellCmds -join \"`n\") }".to_string(), + " if ($LASTEXITCODE -eq 0) { Invoke-PyenvExpression $shellCmds }".to_string(), " }".to_string(), " 'activate' {".to_string(), " $shellCmds = Invoke-PyenvCaptured $pyenvExe (@('sh-activate', '--') + @($arguments))".to_string(), - " if ($LASTEXITCODE -eq 0 -and $shellCmds.Count -gt 0) { Invoke-Expression ($shellCmds -join \"`n\") }".to_string(), + " if ($LASTEXITCODE -eq 0) { Invoke-PyenvExpression $shellCmds }".to_string(), " }".to_string(), " 'deactivate' {".to_string(), " $shellCmds = Invoke-PyenvCaptured $pyenvExe (@('sh-deactivate', '--') + @($arguments))".to_string(), - " if ($LASTEXITCODE -eq 0 -and $shellCmds.Count -gt 0) { Invoke-Expression ($shellCmds -join \"`n\") }".to_string(), + " if ($LASTEXITCODE -eq 0) { Invoke-PyenvExpression $shellCmds }".to_string(), " }".to_string(), " 'rehash' {".to_string(), " $shellCmds = Invoke-PyenvCaptured $pyenvExe (@('sh-rehash') + @($arguments))".to_string(), - " if ($LASTEXITCODE -eq 0 -and $shellCmds.Count -gt 0) { Invoke-Expression ($shellCmds -join \"`n\") }".to_string(), + " if ($LASTEXITCODE -eq 0) { Invoke-PyenvExpression $shellCmds }".to_string(), + " }".to_string(), + // init / virtualenv-init must return stdout on the PowerShell success stream. + // Invoke-PyenvPassthrough inherits the console, so `(pyenv init - pwsh)` captures + // nothing and `iex` fails with "empty string" once this function shadows pyenv.exe + // (duplicate profile lines, nested inits, or re-sourcing $PROFILE). + " { $_ -in @('init', 'virtualenv-init') } {".to_string(), + " $output = Invoke-PyenvCaptured $pyenvExe (@([string]$command) + @($arguments))".to_string(), + " if ($output.Count -gt 0) { $output }".to_string(), " }".to_string(), " default {".to_string(), " Invoke-PyenvPassthrough $pyenvExe (@([string]$command) + @($arguments)) | Out-Null".to_string(), diff --git a/crates/pyenv-core/src/shell/init.rs b/crates/pyenv-core/src/shell/init.rs index 319fc83..bee8d17 100644 --- a/crates/pyenv-core/src/shell/init.rs +++ b/crates/pyenv-core/src/shell/init.rs @@ -65,7 +65,8 @@ pub(super) fn render_init_help(shell: ShellKind) -> Vec { "# Load pyenv automatically by appending".to_string(), "# the following to $PROFILE.CurrentUserCurrentHost:".to_string(), String::new(), - "iex ((pyenv init - pwsh) -join \"`n\")".to_string(), + "$__pyenv_init = (pyenv init - pwsh) -join \"`n\"".to_string(), + "if ($__pyenv_init) { Invoke-Expression $__pyenv_init }".to_string(), String::new(), "# Restart your shell for the changes to take effect.".to_string(), ], diff --git a/crates/pyenv-core/src/shell/tests.rs b/crates/pyenv-core/src/shell/tests.rs index aed1a77..e40efc2 100644 --- a/crates/pyenv-core/src/shell/tests.rs +++ b/crates/pyenv-core/src/shell/tests.rs @@ -207,6 +207,12 @@ fn init_print_for_pwsh_sets_path_env_and_function() { .iter() .any(|line| line.contains("function Invoke-PyenvPassthrough")) ); + assert!( + report + .stdout + .iter() + .any(|line| line.contains("function Invoke-PyenvExpression")) + ); assert!( report .stdout @@ -228,9 +234,16 @@ fn init_print_for_pwsh_sets_path_env_and_function() { assert!(report.stdout.iter().any(|line| { line.contains("Invoke-PyenvPassthrough $pyenvExe (@([string]$command) + @($arguments))") })); + assert!(report.stdout.iter().any(|line| { + line.contains("$_ -in @('init', 'virtualenv-init')") + })); + assert!(report.stdout.iter().any(|line| { + line.contains("if ($output.Count -gt 0) { $output }") + })); assert!(report.stdout.iter().any(|line| { line.contains("Invoke-PyenvCaptured $pyenvExe (@('sh-shell', '--') + @($arguments))") })); + assert!(report.stdout.iter().any(|line| line.contains("Invoke-PyenvExpression"))); assert!(report.stdout.iter().any(|line| line.contains("sh-shell"))); assert!( report @@ -246,6 +259,28 @@ fn init_print_for_pwsh_sets_path_env_and_function() { ); } +#[test] +fn init_help_for_pwsh_guards_empty_invoke_expression() { + let (_temp, ctx) = test_context(); + let help = cmd_init(&ctx, &[String::from("pwsh")]); + assert_eq!(help.exit_code, 1); + assert!( + help.stderr + .iter() + .any(|line| line.contains("$__pyenv_init = (pyenv init - pwsh)")) + ); + assert!( + help.stderr + .iter() + .any(|line| line.contains("if ($__pyenv_init) { Invoke-Expression $__pyenv_init }")) + ); + assert!( + help.stderr + .iter() + .all(|line| !line.contains("iex ((pyenv init - pwsh)")) + ); +} + #[test] fn init_path_no_push_path_guards_duplicate_shims() { let (_temp, ctx) = test_context(); diff --git a/crates/pyenv-gui/src/main.rs b/crates/pyenv-gui/src/main.rs index 0a31d89..738c2f1 100644 --- a/crates/pyenv-gui/src/main.rs +++ b/crates/pyenv-gui/src/main.rs @@ -686,7 +686,7 @@ fn configure_shell(shell_name: String, profile_path: String) -> Result<(), Strin // Format the initialization block to append let init_block = if shell_name.contains("PowerShell") { - "\n# pyenv-native shell initialization\niex ((pyenv init - pwsh) -join \"`n\")\n" + "\n# pyenv-native shell initialization\n$__pyenv_init = (pyenv init - pwsh) -join \"`n\"\nif ($__pyenv_init) { Invoke-Expression $__pyenv_init }\n" } else if shell_name.contains("Zsh") { "\n# pyenv-native shell initialization\neval \"$(pyenv init - zsh)\"\n" } else if shell_name.contains("Bash") { diff --git a/crates/pyenv-gui/tauri.conf.json b/crates/pyenv-gui/tauri.conf.json index 8ef1f02..9b96768 100644 --- a/crates/pyenv-gui/tauri.conf.json +++ b/crates/pyenv-gui/tauri.conf.json @@ -1,6 +1,6 @@ { "productName": "Pyenv Native", - "version": "0.2.35", + "version": "0.2.36", "identifier": "com.pyenv-native.gui", "build": { "frontendDist": "ui" diff --git a/docs/CLI.md b/docs/CLI.md index 41cab91..665d275 100644 --- a/docs/CLI.md +++ b/docs/CLI.md @@ -115,7 +115,8 @@ To enable shims and the `pyenv` shell function, add the following to your shell ### Windows (PowerShell Profile) ```powershell -iex ((pyenv init - pwsh) -join "`n") +$__pyenv_init = (pyenv init - pwsh) -join "`n" +if ($__pyenv_init) { Invoke-Expression $__pyenv_init } ``` ### Bash (`~/.bashrc`) diff --git a/docs/INSTRUCTIONS.md b/docs/INSTRUCTIONS.md index 7b19aea..1b6039b 100644 --- a/docs/INSTRUCTIONS.md +++ b/docs/INSTRUCTIONS.md @@ -280,7 +280,8 @@ After installation, initialize your shell so shim resolution and shell-scoped ve ### PowerShell shell init ```powershell -iex ((pyenv init - pwsh) -join "`n") +$__pyenv_init = (pyenv init - pwsh) -join "`n" +if ($__pyenv_init) { Invoke-Expression $__pyenv_init } ``` ### CMD shell init diff --git a/python-package/pyproject.toml b/python-package/pyproject.toml index 50ca967..c4a26fe 100644 --- a/python-package/pyproject.toml +++ b/python-package/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "hatchling.build" [project] name = "pyenv-native" -version = "0.2.35" +version = "0.2.36" description = "Python install package for the native-first pyenv-native runtime bundles." readme = "README.md" requires-python = ">=3.8" diff --git a/python-package/src/pyenv_native_bootstrap/__init__.py b/python-package/src/pyenv_native_bootstrap/__init__.py index ffbab39..d2bd6a6 100644 --- a/python-package/src/pyenv_native_bootstrap/__init__.py +++ b/python-package/src/pyenv_native_bootstrap/__init__.py @@ -3,4 +3,4 @@ __all__ = ["__version__"] -__version__ = "0.2.35" \ No newline at end of file +__version__ = "0.2.36" \ No newline at end of file diff --git a/scripts/install-pyenv-native.ps1 b/scripts/install-pyenv-native.ps1 index 988d9c0..5303d4c 100644 --- a/scripts/install-pyenv-native.ps1 +++ b/scripts/install-pyenv-native.ps1 @@ -293,7 +293,8 @@ function Update-PowerShellProfileBlock { $block = @( $beginMarker, "if (Test-Path '$escapedInstalledExePath') {", - " iex ((& '$escapedInstalledExePath' init - pwsh) -join ""`n"")", + " `$__pyenv_init = (& '$escapedInstalledExePath' init - pwsh) -join ""`n""", + ' if ($__pyenv_init) { Invoke-Expression $__pyenv_init }', '}', $endMarker ) -join [Environment]::NewLine @@ -308,6 +309,11 @@ function Update-PowerShellProfileBlock { $pattern = [regex]::Escape($beginMarker) + '.*?' + [regex]::Escape($endMarker) if ($existing -match $pattern) { $updated = [regex]::Replace($existing, $pattern, [System.Text.RegularExpressions.MatchEvaluator]{ param($m) $block }, 'Singleline') + } elseif ($existing -match 'pyenv init') { + # Profile already evaluates pyenv init (GUI or manual snippet). Do not append a + # second block — double init made `(pyenv init - pwsh)` hit the shell function, + # which previously discarded stdout and broke Invoke-Expression with an empty string. + return $profilePath } elseif ([string]::IsNullOrWhiteSpace($existing)) { $updated = $block + [Environment]::NewLine } else { diff --git a/scripts/smoke-shells.ps1 b/scripts/smoke-shells.ps1 index 7952d73..46122b6 100644 --- a/scripts/smoke-shells.ps1 +++ b/scripts/smoke-shells.ps1 @@ -57,7 +57,13 @@ $cmdLayout = New-SmokeLayout -Name 'cmd' $pwshCommand = @" `$env:PYENV_ROOT = '$($pwshLayout.PyenvRoot.Replace("'", "''"))' Set-Location '$($pwshLayout.WorkDir.Replace("'", "''"))' -iex ((& '$($resolvedPyenvExe.Replace("'", "''"))' init --no-rehash - pwsh) -join [Environment]::NewLine) +`$__pyenv_init = (& '$($resolvedPyenvExe.Replace("'", "''"))' init --no-rehash - pwsh) -join [Environment]::NewLine +if (-not `$__pyenv_init) { throw 'Expected non-empty pyenv init output' } +Invoke-Expression `$__pyenv_init +# Regression: init must still return capturable stdout after the pyenv function shadows the exe. +`$__pyenv_init2 = (pyenv init --no-rehash - pwsh) -join [Environment]::NewLine +if (-not `$__pyenv_init2) { throw 'pyenv init returned empty after function load (stdout not pipelined)' } +if (`$__pyenv_init2 -notmatch 'function pyenv') { throw 'Captured init output missing pyenv function' } pyenv shell 3.13.12 if (`$LASTEXITCODE -ne 0) { exit `$LASTEXITCODE } `$result = & '$($resolvedPyenvExe.Replace("'", "''"))' version-name @@ -68,7 +74,12 @@ if ((`$result | Select-Object -Last 1).Trim() -ne '3.13.12') { throw 'Expected v $ps5Command = @" `$env:PYENV_ROOT = '$($ps5Layout.PyenvRoot.Replace("'", "''"))' Set-Location '$($ps5Layout.WorkDir.Replace("'", "''"))' -iex ((& '$($resolvedPyenvExe.Replace("'", "''"))' init --no-rehash - pwsh) -join [Environment]::NewLine) +`$__pyenv_init = (& '$($resolvedPyenvExe.Replace("'", "''"))' init --no-rehash - pwsh) -join [Environment]::NewLine +if (-not `$__pyenv_init) { throw 'Expected non-empty pyenv init output' } +Invoke-Expression `$__pyenv_init +`$__pyenv_init2 = (pyenv init --no-rehash - pwsh) -join [Environment]::NewLine +if (-not `$__pyenv_init2) { throw 'pyenv init returned empty after function load (stdout not pipelined)' } +if (`$__pyenv_init2 -notmatch 'function pyenv') { throw 'Captured init output missing pyenv function' } pyenv shell 3.13.12 if (`$LASTEXITCODE -ne 0) { exit `$LASTEXITCODE } `$result = & '$($resolvedPyenvExe.Replace("'", "''"))' version-name From def3e2a1991d5b1df680a9fc4db9cf8587b2c2ee Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Thu, 13 Aug 2026 07:27:27 +0000 Subject: [PATCH 2/2] fix(gui): Host Environment ignore shell PATH noise; refresh stack MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Windows Host Environment was "Needs attention" whenever doctor warned about process PATH/shims/selection—common for desktop GUI launches even when install readiness is fine. Verdict now uses install-relevant checks only, and the panel surfaces install warnings. Also bump to v0.2.37: rmcp 3.1.2, clap 4.6.6, thiserror/toml minors, setup-python@v7 + Python 3.13, setup-node@v7 (Node 24) for a11y, rust-cache, axe-core/jsdom latest. Tauri already at 2.11.5 / Rust stable 1.97.1. Co-authored-by: I'm Your Boy Roy --- .github/workflows/ci.yml | 42 +- .github/workflows/release.yml | 37 +- Cargo.lock | 403 ++++++++++----- Cargo.toml | 2 +- crates/pyenv-cli/Cargo.toml | 2 +- crates/pyenv-core/Cargo.toml | 4 +- crates/pyenv-core/src/preflight/intel.rs | 53 +- crates/pyenv-core/src/preflight/tests.rs | 50 ++ crates/pyenv-core/src/preflight/types.rs | 24 +- crates/pyenv-core/src/runtime/tests.rs | 4 +- crates/pyenv-core/src/shell/tests.rs | 25 +- crates/pyenv-gui/tauri.conf.json | 2 +- crates/pyenv-gui/ui/app.js | 37 +- crates/pyenv-mcp/Cargo.toml | 4 +- python-package/pyproject.toml | 2 +- .../src/pyenv_native_bootstrap/__init__.py | 2 +- scripts/gui-a11y/package-lock.json | 468 +++++++++--------- scripts/gui-a11y/package.json | 4 +- 18 files changed, 723 insertions(+), 442 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index f4dd7a2..9f60dcb 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -28,10 +28,13 @@ jobs: with: components: rustfmt, clippy + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Install dependencies (Linux) run: | @@ -54,6 +57,11 @@ jobs: shell: bash run: sh ./scripts/check-gui-patterns.sh + - name: Setup Node.js + uses: actions/setup-node@v7 + with: + node-version: "24" + - name: GUI accessibility audit shell: bash run: | @@ -101,10 +109,13 @@ jobs: targets: x86_64-pc-windows-msvc components: rustfmt + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Test Rust workspace shell: pwsh @@ -152,6 +163,9 @@ jobs: toolchain: stable-x86_64-pc-windows-msvc targets: aarch64-pc-windows-msvc + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Build Windows ARM64 release bundle smoke test shell: pwsh run: powershell -ExecutionPolicy Bypass -File .\scripts\build-release-bundle.ps1 -TargetTriple aarch64-pc-windows-msvc @@ -168,6 +182,9 @@ jobs: with: targets: aarch64-unknown-linux-musl + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Install Cross run: cargo install cross --locked @@ -195,6 +212,9 @@ jobs: with: targets: aarch64-linux-android + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Install cargo-ndk run: cargo install cargo-ndk --locked @@ -218,10 +238,13 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Test Rust workspace shell: bash @@ -245,10 +268,13 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Test Rust workspace shell: bash diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 2bd21fa..0f3aca9 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -30,10 +30,13 @@ jobs: targets: x86_64-pc-windows-msvc components: rustfmt + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Version sync check shell: pwsh @@ -97,6 +100,9 @@ jobs: toolchain: stable-x86_64-pc-windows-msvc targets: aarch64-pc-windows-msvc + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Build Windows ARM64 release bundle shell: pwsh run: powershell -ExecutionPolicy Bypass -File .\scripts\build-release-bundle.ps1 -TargetTriple aarch64-pc-windows-msvc @@ -119,10 +125,13 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Install dependencies (Linux) run: | @@ -168,6 +177,9 @@ jobs: with: targets: aarch64-unknown-linux-musl + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Install Cross run: cargo install cross --locked @@ -203,6 +215,9 @@ jobs: with: targets: aarch64-linux-android + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Install cargo-ndk run: cargo install cargo-ndk --locked @@ -234,10 +249,13 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Test Rust workspace shell: bash @@ -276,10 +294,13 @@ jobs: - name: Install Rust toolchain uses: dtolnay/rust-toolchain@stable + - name: Rust cache + uses: Swatinem/rust-cache@v2 + - name: Setup Python - uses: actions/setup-python@v6 + uses: actions/setup-python@v7 with: - python-version: "3.12" + python-version: "3.13" - name: Test Rust workspace shell: bash diff --git a/Cargo.lock b/Cargo.lock index e79783e..b73dda7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -10,9 +10,9 @@ checksum = "320119579fcad9c21884f5c4861d16174d0e06250625266f50fe6898340abefa" [[package]] name = "aho-corasick" -version = "1.1.4" +version = "1.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ddd31a130427c27518df266943a5308ed92d4b226cc639f5a8f1002816174301" +checksum = "c982642fa9e8606056828ee9a8505737230110bb1099153c79efe865c59d12ba" dependencies = [ "memchr", ] @@ -34,9 +34,9 @@ dependencies = [ [[package]] name = "android_system_properties" -version = "0.1.5" +version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +checksum = "ae221649c9976a6f6c56ae1facf410f3ddb33cc661c4b7b61020a912d4237fbc" dependencies = [ "libc", ] @@ -107,17 +107,6 @@ dependencies = [ "serde_json", ] -[[package]] -name = "async-trait" -version = "0.1.91" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae36dc4177970ef04fde5178d3e2429882def40e57a451f919c098f72baa6cec" -dependencies = [ - "proc-macro2", - "quote", - "syn 3.0.3", -] - [[package]] name = "atk" version = "0.18.2" @@ -155,9 +144,9 @@ checksum = "f2032f911046de80f0a198e0901378627c33f59ea0ac00e363d481118bd70a53" [[package]] name = "aws-lc-rs" -version = "1.17.3" +version = "1.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "00bdb5da18dac48ca2cc7cd4a98e533e8635a58e2361d13a1a4ee3888e0d72f1" +checksum = "ce2b2dcc879c3bae0d371e77c99f2238400ef24ec001394befa67b6e543add9e" dependencies = [ "aws-lc-sys", "zeroize", @@ -165,9 +154,9 @@ dependencies = [ [[package]] name = "aws-lc-sys" -version = "0.43.0" +version = "0.44.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43103168cc76fe62678a375e722fc9cb3a0146159ac5828bc4f0dfd755c2224c" +checksum = "f09fae7be8bb3174e05c6afdb34199e6dc0c7c04ba9fa237b1967adfbde27483" dependencies = [ "cc", "cmake", @@ -188,6 +177,12 @@ version = "0.22.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6" +[[package]] +name = "base64" +version = "0.23.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac07cdecf99051d9a5238b80f35af32cdeba5b336e55d957b318b50137e18da5" + [[package]] name = "bit-set" version = "0.8.0" @@ -356,7 +351,7 @@ dependencies = [ "semver", "serde", "serde_json", - "thiserror 2.0.19", + "thiserror 2.0.20", ] [[package]] @@ -371,9 +366,9 @@ dependencies = [ [[package]] name = "cc" -version = "1.4.0" +version = "1.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5add81bb678e6cb321aff7fa0dc7689ad82b112dbc032cea19f91d6b8e3582b9" +checksum = "5d262e149917187838d5b42777c8253bcb64500067342904e7d429499a6f277e" dependencies = [ "find-msvc-tools", "jobserver", @@ -445,9 +440,9 @@ dependencies = [ [[package]] name = "clap" -version = "4.6.4" +version = "4.6.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d91e0c145792ef73a6ad36d27c75ac09f1832222a3c209689d90f534685ee5b7" +checksum = "473c7e07f409a8d772161724aa8db6a765a2532a70f9667eeb7b49d3d02fbdca" dependencies = [ "clap_builder", "clap_derive", @@ -455,9 +450,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.6.2" +version = "4.6.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f09628afdcc538b57f3c6341e9c8e9970f18e4a481690a64974d7023bd33548b" +checksum = "7b48fea5a88e9ae728a2dcbedbfc0e730f7d60da42e1cb049a83c9fb8b789889" dependencies = [ "anstream", "anstyle", @@ -519,9 +514,9 @@ dependencies = [ [[package]] name = "cookie" -version = "0.18.1" +version = "0.18.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ddef33a339a91ea89fb53151bd0a4689cfce27055c291dfa69945475d22c747" +checksum = "1a373e3602691c3cdea496d2f0ee5935151e6168fe87739483c463db1b2f2f87" dependencies = [ "time", "version_check", @@ -664,8 +659,18 @@ version = "0.23.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "25ae13da2f202d56bd7f91c25fba009e7717a1e4a1cc98a76d844b65ae912e9d" dependencies = [ - "darling_core", - "darling_macro", + "darling_core 0.23.0", + "darling_macro 0.23.0", +] + +[[package]] +name = "darling" +version = "0.24.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88490bf1b990d87eaaa7ac8aa887f629a08e7359765b4911faf63c3763347d23" +dependencies = [ + "darling_core 0.24.0", + "darling_macro 0.24.0", ] [[package]] @@ -681,17 +686,41 @@ dependencies = [ "syn 2.0.119", ] +[[package]] +name = "darling_core" +version = "0.24.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "084e274f91c482280130e1e34e0b8d6e66776a060d7b6de7b84289ca778868c4" +dependencies = [ + "ident_case", + "proc-macro2", + "quote", + "strsim", + "syn 3.0.3", +] + [[package]] name = "darling_macro" version = "0.23.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ac3984ec7bd6cfa798e62b4a642426a5be0e68f9401cfc2a01e3fa9ea2fcdb8d" dependencies = [ - "darling_core", + "darling_core 0.23.0", "quote", "syn 2.0.119", ] +[[package]] +name = "darling_macro" +version = "0.24.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68f5792fa0d41cd2325ce0ffa64f0a340eaebd4971a3a0c5e1ffd2cc488a355e" +dependencies = [ + "darling_core 0.24.0", + "quote", + "syn 3.0.3", +] + [[package]] name = "dbus" version = "0.9.12" @@ -703,6 +732,37 @@ dependencies = [ "windows-sys 0.61.2", ] +[[package]] +name = "defmt" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2953bfe4f93bbd20cc71198842756f77d161884c99ebbabc41d80231ded88d1" +dependencies = [ + "bitflags 1.3.2", + "defmt-macros", +] + +[[package]] +name = "defmt-macros" +version = "1.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bad9c72e7ca2137e0dc3813245a0d282fd6daad32fd800af018306a9169b5fe8" +dependencies = [ + "defmt-parser", + "proc-macro2", + "quote", + "syn 2.0.119", +] + +[[package]] +name = "defmt-parser" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "10d60334b3b2e7c9d91ef8150abfb6fa4c1c39ebbcf4a81c2e346aad939fee3e" +dependencies = [ + "thiserror 2.0.20", +] + [[package]] name = "deranged" version = "0.5.8" @@ -900,7 +960,7 @@ dependencies = [ "cc", "memchr", "rustc_version", - "toml 1.1.3+spec-1.1.0", + "toml 1.1.4+spec-1.1.0", "vswhom", "winreg", ] @@ -975,9 +1035,9 @@ dependencies = [ [[package]] name = "find-msvc-tools" -version = "0.1.9" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5baebc0774151f905a1a2cc41989300b1e6fbb29aff0ceffa1064fdd3088d582" +checksum = "26b73573e6edcd2af0cdf47bd6cb58f0b3839491263c314eaad1ccf24430e1de" [[package]] name = "flate2" @@ -1046,9 +1106,9 @@ checksum = "42703706b716c37f96a77aea830392ad231f44c9e9a67872fa5548707e11b11c" [[package]] name = "futures" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a88cf1f829d945f548cf8fec32c61b1f202b6d93b45848602fc02af4b12ad218" +checksum = "9a31d2a3fbaaeb2af2368bbdd904aa8e812d3c04a1ee10d3171f52d556e5d0a3" dependencies = [ "futures-channel", "futures-core", @@ -1061,9 +1121,9 @@ dependencies = [ [[package]] name = "futures-channel" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "262590f4fe6afeb0bc83be1daa64e52657fe185690a958af7f3ad0e92085c5ae" +checksum = "b1f9e3d69d39e4862ffed03ed071a76f9a13ba1d9109d355b0f0aa6b15e393c4" dependencies = [ "futures-core", "futures-sink", @@ -1071,15 +1131,15 @@ dependencies = [ [[package]] name = "futures-core" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2cd50c473c80f6d7c3670a752354b8e569b1a7cbfdc0419ec88e5edad85e0dc7" +checksum = "92d699e522242e69e3003b94ecc1f960f3a5e015aa7c5d7486e65ad01dd94f5e" [[package]] name = "futures-executor" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6754879cc9f2c66f88c6e5c35344bb0bdb0708b0352b1201815667c7eabc7458" +checksum = "031b47cf1a3c6cc8bc2fc76cd437f521619387907d469316e7c0bc278f1f5432" dependencies = [ "futures-core", "futures-task", @@ -1088,38 +1148,38 @@ dependencies = [ [[package]] name = "futures-io" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4577ecaa3c4f96589d473f679a71b596316f6641bc350038b962a5daf0085d7a" +checksum = "53c0fa8157de1303bfffdaa1cc2a673bfffb60102f76b0ef4441659124373fed" [[package]] name = "futures-macro" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d6d3cde68c518367be28956066ddfef33813991b77a55005a69dae04bf3b10b" +checksum = "9fb9654ba8355388abeb8dcb4fc62f511300867002afc858860463bdd9fe0c44" dependencies = [ "proc-macro2", "quote", - "syn 2.0.119", + "syn 3.0.3", ] [[package]] name = "futures-sink" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e34418ac499d6305c2fb5ad0ed2f6ac998c5f8ca209b4510f7f94242c647e307" +checksum = "1944426bf7d03f1d14f708785e4b33efd750b36d48a157b836b3efc15ede8e1d" [[package]] name = "futures-task" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b231ed28831efb4a61a08580c4bc233ec56bc009f4cd8f52da2c3cb97df0c109" +checksum = "cd417de3d1d015fc3bfd2b1ea46dfc7bab72ef86f1cc7cc9c78e728b34a6d1fd" [[package]] name = "futures-util" -version = "0.3.33" +version = "0.3.34" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a77a90a256fce34da66415271e30f94ee91c57b04b8a2c042d9cf3220179deaa" +checksum = "0d50a92467f8ba5dd6e3ee5d4bd04d73ab2e4e1c44474a0674821dfce14b79bc" dependencies = [ "futures-channel", "futures-core", @@ -1489,9 +1549,9 @@ dependencies = [ [[package]] name = "http" -version = "1.4.2" +version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6970f50e31d6fc17d3fa27329444bfa74e196cf62e95052a3f6fee181dba6425" +checksum = "918d3568bebf352712bc2ef3d46a8bcf1a75b373be6539de198e9105cbbf9ce0" dependencies = [ "bytes", "itoa", @@ -1509,9 +1569,9 @@ dependencies = [ [[package]] name = "http-body-util" -version = "0.1.4" +version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e9f41fd6a08e4d4ec69df65976da761afd5ad5e58a9d4acb46bd1c953a9e3ff2" +checksum = "23169fe34a5fbcdd3f3862e78fb9b6fccd5f02a6dc6f732547005d45631ce71c" dependencies = [ "bytes", "futures-core", @@ -1769,9 +1829,9 @@ dependencies = [ [[package]] name = "ipnet" -version = "2.12.0" +version = "2.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d98f6fed1fde3f8c21bc40a1abb88dd75e67924f9cffc3ef95607bad8017f8e2" +checksum = "6a756c3fac73139e83f14c2d742155dd2b78d3ee56597b419a0579b7bdd6dd78" [[package]] name = "is_terminal_polyfill" @@ -1808,6 +1868,59 @@ dependencies = [ "system-deps", ] +[[package]] +name = "jiff" +version = "0.2.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "668b7183bd07af9a4885f5c35b0cc5c83c4607a913c16b7e17291832910d2dcc" +dependencies = [ + "defmt", + "jiff-core", + "jiff-static", + "jiff-tzdb-platform", + "log", + "portable-atomic", + "portable-atomic-util", + "serde_core", + "windows-link 0.2.1", +] + +[[package]] +name = "jiff-core" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7feca88439efe53da3754500c1851dedf3cb36c524dd5cf8225cc0794de95d09" +dependencies = [ + "defmt", +] + +[[package]] +name = "jiff-static" +version = "0.2.35" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3a69dcb3a21cfb32ce1cd056169337ca284af0766dd766e7878819b251a49204" +dependencies = [ + "jiff-core", + "proc-macro2", + "quote", + "syn 2.0.119", +] + +[[package]] +name = "jiff-tzdb" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "142bd39932ad231f10513df9ab62661fead8719872150b7ad02a2df79f4e141e" + +[[package]] +name = "jiff-tzdb-platform" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "875a5a69ac2bab1a891711cf5eccbec1ce0341ea805560dcd90b7a2e925132e8" +dependencies = [ + "jiff-tzdb", +] + [[package]] name = "jni" version = "0.21.1" @@ -1836,7 +1949,7 @@ dependencies = [ "jni-sys 0.4.1", "log", "simd_cesu8", - "thiserror 2.0.19", + "thiserror 2.0.20", "walkdir", "windows-link 0.2.1", ] @@ -1894,9 +2007,9 @@ dependencies = [ [[package]] name = "js-sys" -version = "0.3.103" +version = "0.3.104" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53b44bfcdb3f8d5837a46dae1ca9660a837176eee74a28b229bc626816589102" +checksum = "0e0c1080212aad755ea003d18543e8768dd432c48819efd73a7bf1e39b7a5a3a" dependencies = [ "cfg-if", "futures-util", @@ -2003,9 +2116,9 @@ dependencies = [ [[package]] name = "libredox" -version = "0.1.18" +version = "0.1.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c943259e342f1e06ff2da7a83eabdfe7f92ce10262688dbf1895ff0b3e6e4652" +checksum = "2026a5056764a10b2bf5d56488cba40da507f5493a6a429340e2004d9ed085fa" dependencies = [ "libc", ] @@ -2138,7 +2251,7 @@ dependencies = [ "once_cell", "png 0.18.1", "serde", - "thiserror 2.0.19", + "thiserror 2.0.20", "windows-sys 0.61.2", ] @@ -2598,6 +2711,21 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2f3a9f18d041e6d0e102a0a46750538147e5e8992d3b4873aaafee2520b00ce3" +[[package]] +name = "portable-atomic" +version = "1.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05c8b63e8d9609db387f0324918f81d68fe27748f084ef092fb35954d0539a85" + +[[package]] +name = "portable-atomic-util" +version = "0.2.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c2a106d1259c23fac8e543272398ae0e3c0b8d33c88ed73d0cc71b0f1d902618" +dependencies = [ + "portable-atomic", +] + [[package]] name = "potential_utf" version = "0.1.5" @@ -2692,7 +2820,7 @@ dependencies = [ [[package]] name = "pyenv-cli" -version = "0.2.36" +version = "0.2.37" dependencies = [ "anyhow", "clap", @@ -2701,7 +2829,7 @@ dependencies = [ [[package]] name = "pyenv-core" -version = "0.2.36" +version = "0.2.37" dependencies = [ "anyhow", "bzip2", @@ -2712,14 +2840,14 @@ dependencies = [ "serde_json", "tar", "tempfile", - "thiserror 2.0.19", - "toml 1.1.3+spec-1.1.0", + "thiserror 2.0.20", + "toml 1.1.4+spec-1.1.0", "zip", ] [[package]] name = "pyenv-gui" -version = "0.2.36" +version = "0.2.37" dependencies = [ "pyenv-core", "rfd", @@ -2732,7 +2860,7 @@ dependencies = [ [[package]] name = "pyenv-mcp" -version = "0.2.36" +version = "0.2.37" dependencies = [ "anyhow", "clap", @@ -2768,7 +2896,7 @@ dependencies = [ "rustc-hash", "rustls", "socket2", - "thiserror 2.0.19", + "thiserror 2.0.20", "tokio", "tracing", "web-time", @@ -2791,7 +2919,7 @@ dependencies = [ "rustls", "rustls-pki-types", "slab", - "thiserror 2.0.19", + "thiserror 2.0.20", "tinyvec", "tracing", "web-time", @@ -2910,7 +3038,7 @@ checksum = "a4e608c6638b9c18977b00b475ac1f28d14e84b27d8d42f70e0bf1e3dec127ac" dependencies = [ "getrandom 0.2.17", "libredox", - "thiserror 2.0.19", + "thiserror 2.0.20", ] [[package]] @@ -2947,9 +3075,9 @@ dependencies = [ [[package]] name = "regex-automata" -version = "0.4.16" +version = "0.4.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8fcfdb36bda0c880c5931cdc7a2bcdc8ba4556847b9d912bca70bc94708711ad" +checksum = "ad8553b9b26413251cbf30e620595c7a41b3887f03da04579c0e6b0d6a06b4b2" dependencies = [ "aho-corasick", "memchr", @@ -3046,12 +3174,11 @@ dependencies = [ [[package]] name = "rmcp" -version = "2.2.0" +version = "3.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "14db48ee17a9ba61810ab1a9c1beb7d06d8136ae39ac25a1137f10d357af01af" +checksum = "c8dddc5b1924b9a59fba420166160ca2c4663a4e01803e52eda33070f56d63c8" dependencies = [ - "async-trait", - "base64 0.22.1", + "base64 0.23.1", "chrono", "futures", "pastey", @@ -3060,23 +3187,24 @@ dependencies = [ "schemars 1.2.2", "serde", "serde_json", - "thiserror 2.0.19", + "thiserror 2.0.20", "tokio", "tokio-util", "tracing", + "uuid", ] [[package]] name = "rmcp-macros" -version = "2.2.0" +version = "3.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "783d787bf21813b285f13019adc49e11af501c658890c1e519f31f937c68b7e3" +checksum = "6898e24cd16342b59bfa8a53c2c04b9cf62fc8a2cfea57b9c038b09984bfc521" dependencies = [ - "darling", + "darling 0.24.0", "proc-macro2", "quote", "serde_json", - "syn 2.0.119", + "syn 3.0.3", ] [[package]] @@ -3109,9 +3237,9 @@ dependencies = [ [[package]] name = "rustls" -version = "0.23.42" +version = "0.23.43" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3c54fcab019b409d04215d3a17cb438fd7fbf192ee61461f20f4fe18704bc138" +checksum = "0283386ce02abc0151e1761d08802dfe86c173b0b494af5cbc086574e453da06" dependencies = [ "aws-lc-rs", "once_cell", @@ -3172,9 +3300,9 @@ checksum = "f87165f0995f63a9fbeea62b64d10b4d9d8e78ec6d7d51fb2125fda7bb36788f" [[package]] name = "rustls-webpki" -version = "0.103.13" +version = "0.103.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "61c429a8649f110dddef65e2a5ad240f747e85f7758a6bccc7e5777bd33f756e" +checksum = "0527518605e68109d875e248ea259b6758801cf165e4b2c2733ae3b51f12535a" dependencies = [ "aws-lc-rs", "ring", @@ -3461,9 +3589,9 @@ dependencies = [ [[package]] name = "serde_with" -version = "3.21.0" +version = "3.22.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "76a5c54c7310e7b8b9577c286d7e399ddd876c3e12b3ed917a8aabc4b96e9e8c" +checksum = "ee78f1fbe43ac4a0e47aadb3dbd357b69eb0d3793e948624cd03dd2750ab1c0a" dependencies = [ "base64 0.22.1", "bs58", @@ -3471,6 +3599,7 @@ dependencies = [ "hex", "indexmap 1.9.3", "indexmap 2.14.0", + "jiff", "schemars 0.9.0", "schemars 1.2.2", "serde_core", @@ -3481,11 +3610,11 @@ dependencies = [ [[package]] name = "serde_with_macros" -version = "3.21.0" +version = "3.22.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "84d57bc0c8b9a17920c178daa6bb924850d54a9c97ab45194bb8c17ad66bb660" +checksum = "8705578779c2b6bd90d84d66eb2e206b708b1a4d7b9f17641b293545bf1c7e46" dependencies = [ - "darling", + "darling 0.23.0", "proc-macro2", "quote", "syn 2.0.119", @@ -3813,9 +3942,9 @@ dependencies = [ [[package]] name = "tao-macros" -version = "0.1.3" +version = "0.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f4e16beb8b2ac17db28eab8bca40e62dbfbb34c0fcdc6d9826b11b7b5d047dfd" +checksum = "5f7eeb6d99155545da6150a1795945f16ac9c178deb2a5f2e74d776107bd5849" dependencies = [ "proc-macro2", "quote", @@ -3880,7 +4009,7 @@ dependencies = [ "tauri-runtime", "tauri-runtime-wry", "tauri-utils", - "thiserror 2.0.19", + "thiserror 2.0.20", "tokio", "tray-icon", "url", @@ -3931,7 +4060,7 @@ dependencies = [ "sha2", "syn 2.0.119", "tauri-utils", - "thiserror 2.0.19", + "thiserror 2.0.20", "time", "url", "uuid", @@ -3970,7 +4099,7 @@ dependencies = [ "serde", "serde_json", "tauri-utils", - "thiserror 2.0.19", + "thiserror 2.0.20", "url", "webkit2gtk", "webview2-com", @@ -4033,8 +4162,8 @@ dependencies = [ "serde_json", "serde_with", "swift-rs", - "thiserror 2.0.19", - "toml 1.1.3+spec-1.1.0", + "thiserror 2.0.20", + "toml 1.1.4+spec-1.1.0", "url", "urlpattern", "uuid", @@ -4049,7 +4178,7 @@ checksum = "cc65d45c68858bfe420dd29e834b5d15dbecf8a07a8a16cf4d532c7b1f69d4b6" dependencies = [ "dunce", "embed-resource", - "toml 1.1.3+spec-1.1.0", + "toml 1.1.4+spec-1.1.0", ] [[package]] @@ -4085,11 +4214,11 @@ dependencies = [ [[package]] name = "thiserror" -version = "2.0.19" +version = "2.0.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09a43598840e33d5b0331f38c5e30d13bb11c11210a4b58f0d9b18a5a5eefcd9" +checksum = "ec86235f5fcc2a73650310756d2ac5b138a5780bbbdfae3eeccec992c435ba4f" dependencies = [ - "thiserror-impl 2.0.19", + "thiserror-impl 2.0.20", ] [[package]] @@ -4105,9 +4234,9 @@ dependencies = [ [[package]] name = "thiserror-impl" -version = "2.0.19" +version = "2.0.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "43cbfe0cf76104d42a574802844187e84a305e531ed54455f11fbde0f10541cd" +checksum = "bc04cd3e1236dd4a98afca4569f2deb3f120e5422a4023be2cb683f8486292af" dependencies = [ "proc-macro2", "quote", @@ -4116,9 +4245,9 @@ dependencies = [ [[package]] name = "time" -version = "0.3.54" +version = "0.3.55" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3e1d5e639ff6bab73cb6885cc7e7b1de96c3f32c68ec55f3952614bec1092244" +checksum = "cdb87b95ec50ddfa440816d227a17b2ccbdda963a316a727fda0fc4334f7d134" dependencies = [ "deranged", "num-conv", @@ -4188,13 +4317,13 @@ dependencies = [ [[package]] name = "tokio-macros" -version = "2.7.1" +version = "2.7.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6328af13490e73a9b4694030fafd93f8c8c6a9dede33e821c3fc63eddf8042ba" +checksum = "78773a2a397f451582ce068015985c33193cf6dea8b74d2a639fe457b2f07b0e" dependencies = [ "proc-macro2", "quote", - "syn 2.0.119", + "syn 3.0.3", ] [[package]] @@ -4250,9 +4379,9 @@ dependencies = [ [[package]] name = "toml" -version = "1.1.3+spec-1.1.0" +version = "1.1.4+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "53c96ecdfa941c8fc4fcaed14f99ada8ebed502eef533015095a07e3301d4c3c" +checksum = "3aace63f4bbcdfc2c965b059de67119c89c4017a70d633be6c104910f67056f5" dependencies = [ "indexmap 2.14.0", "serde_core", @@ -4435,7 +4564,7 @@ dependencies = [ "once_cell", "png 0.18.1", "serde", - "thiserror 2.0.19", + "thiserror 2.0.20", "windows-sys 0.61.2", ] @@ -4639,9 +4768,9 @@ dependencies = [ [[package]] name = "wasm-bindgen" -version = "0.2.126" +version = "0.2.127" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4b067c0c11094aef6b7a801c1e34a26affafdf3d051dba08456b868789aaf9a4" +checksum = "1b70935747edd64d89de3efa29d73789b806c15798f8e7dca4d8ac356b50ce70" dependencies = [ "cfg-if", "once_cell", @@ -4652,9 +4781,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-futures" -version = "0.4.76" +version = "0.4.77" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c62df1340f32221cb9c54d6a27b030e3dba64361d4a95bed55f9aacb44da291d" +checksum = "6b7777d5cc23d0e91404e53ce2d5e8ec7acae3026b16233dba62cd3246457950" dependencies = [ "js-sys", "wasm-bindgen", @@ -4662,9 +4791,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.126" +version = "0.2.127" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "167ce5e579f6bcf889c4f7175a8a5a585de84e8ff93976ce393efa5f2837aab1" +checksum = "77775f8f3f7217702089053b94958f8f54061a3f663417df76e19cbdcca29bc1" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -4672,9 +4801,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.126" +version = "0.2.127" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3997c7839262f4ef12cf90b818d6340c18e80f263f1a94bf157d0ec4420380e" +checksum = "e11d33f857dc2fb11b8bc75aee111aa9cbeb12cd9f25efd3d4c2a3dd4e235284" dependencies = [ "bumpalo", "proc-macro2", @@ -4685,9 +4814,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.126" +version = "0.2.127" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dc1b4cb0cc549fcf58d7dfc081778139b3d283a081644e833e84682ad71cea24" +checksum = "7ef64dbcc55df09c7e5a46182d181c2cfa3e925f3da937ea764728b4bbb9dcbf" dependencies = [ "unicode-ident", ] @@ -4767,9 +4896,9 @@ dependencies = [ [[package]] name = "web-sys" -version = "0.3.103" +version = "0.3.104" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8622dcb61c0bcc9fffa6938bed81210af2da9a7e4a1a834b2e37a59b6dfb6141" +checksum = "c435338968042f4f59a557f690a253676d47ce13ceb55d70100e7facf6620a30" dependencies = [ "js-sys", "wasm-bindgen", @@ -4787,9 +4916,9 @@ dependencies = [ [[package]] name = "web_atoms" -version = "0.2.5" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "075474b12bcb3d2e3d4546580e9de478eeeead668a1761e2a8860c836b7ef297" +checksum = "ba8b815c1b593dc0baf78dd0f4fc8fdb2de53198fb1163738093e9a311c33fb3" dependencies = [ "phf", "phf_codegen", @@ -4881,7 +5010,7 @@ version = "0.38.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "381336cfffd772377d291702245447a5251a2ffa5bad679c99e61bc48bacbf9c" dependencies = [ - "thiserror 2.0.19", + "thiserror 2.0.20", "windows", "windows-core 0.61.2", ] @@ -5325,7 +5454,7 @@ dependencies = [ "sha2", "soup3", "tao-macros", - "thiserror 2.0.19", + "thiserror 2.0.20", "url", "webkit2gtk", "webkit2gtk-sys", @@ -5392,18 +5521,18 @@ dependencies = [ [[package]] name = "zerocopy" -version = "0.8.55" +version = "0.8.56" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5a105cd7b140f6eeec8acff2ea38135d3cab283ada58540f629fe51e46696eb" +checksum = "556764e583adb45a9f8d413c2a147fa7e8d821e48e12b14fd560b607998b75eb" dependencies = [ "zerocopy-derive", ] [[package]] name = "zerocopy-derive" -version = "0.8.55" +version = "0.8.56" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fe976fb70c78cd64cccfe3a6fc142244e8a77b70959b30faf9d0ac37ee228eb" +checksum = "f2ab42fc20575779bd240faa45f94a74256f755c0fa9e89f0ede20d91d0cdfc1" dependencies = [ "proc-macro2", "quote", @@ -5486,9 +5615,9 @@ dependencies = [ [[package]] name = "zlib-rs" -version = "0.6.6" +version = "0.6.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b142a20ec14a91d5bc708c1dc21b080c550113d8aa77afa29635673a65dd02c5" +checksum = "34b31d188d9d685a4f9c7b46d6e36631b07058d2cfe190267adce54dc230bf12" [[package]] name = "zmij" diff --git a/Cargo.toml b/Cargo.toml index be747a8..f5b25ea 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,4 +8,4 @@ resolver = "2" [workspace.package] edition = "2024" license = "MIT" -version = "0.2.36" \ No newline at end of file +version = "0.2.37" \ No newline at end of file diff --git a/crates/pyenv-cli/Cargo.toml b/crates/pyenv-cli/Cargo.toml index fb2c1a6..a28e1ef 100644 --- a/crates/pyenv-cli/Cargo.toml +++ b/crates/pyenv-cli/Cargo.toml @@ -6,7 +6,7 @@ license.workspace = true [dependencies] anyhow = "^1.0.104" -clap = { version = "^4.6.4", features = ["derive"] } +clap = { version = "^4.6.6", features = ["derive"] } pyenv-core = { path = "../pyenv-core" } [[bin]] diff --git a/crates/pyenv-core/Cargo.toml b/crates/pyenv-core/Cargo.toml index b484d96..2259f0c 100644 --- a/crates/pyenv-core/Cargo.toml +++ b/crates/pyenv-core/Cargo.toml @@ -12,8 +12,8 @@ reqwest = { version = "^0.13.4", default-features = false, features = ["blocking serde = { version = "^1.0.229", features = ["derive"] } serde_json = "^1.0.151" tar = "^0.4.46" -thiserror = "^2.0.19" -toml = "^1.1.3" +thiserror = "^2.0.20" +toml = "^1.1.4" zip = { version = "^8.6.0", default-features = false, features = ["deflate"] } [dev-dependencies] diff --git a/crates/pyenv-core/src/preflight/intel.rs b/crates/pyenv-core/src/preflight/intel.rs index b18a403..b055b84 100644 --- a/crates/pyenv-core/src/preflight/intel.rs +++ b/crates/pyenv-core/src/preflight/intel.rs @@ -11,7 +11,10 @@ use crate::install::resolve_install_plan; use super::android::inspect_android_toolchain; use super::macos::inspect_macos_toolchain; -use super::types::{PlatformFact, PlatformIntelligence, PreflightVerdict}; +use super::types::{ + PlatformFact, PlatformIntelligence, PreflightVerdict, affects_install_readiness, + is_blocking_check, +}; pub fn build_platform_intelligence(ctx: &AppContext) -> PlatformIntelligence { let os = env::consts::OS.to_string(); @@ -33,12 +36,15 @@ pub fn build_platform_intelligence(ctx: &AppContext) -> PlatformIntelligence { let mut warnings = Vec::new(); for check in &checks { match check.status { - DoctorStatus::Warn if is_install_blocker(&check.name) => { + DoctorStatus::Warn if is_blocking_check(&check.name) => { blocking_issues.push(format!("{}: {}", check.name, check.detail)); } - DoctorStatus::Warn => { + DoctorStatus::Warn if affects_install_readiness(&check.name) => { warnings.push(format!("{}: {}", check.name, check.detail)); } + // Shell PATH / shim / selection health stay in doctor output; they do not + // dilute Host Environment install-readiness. + DoctorStatus::Warn => {} _ => {} } } @@ -63,10 +69,10 @@ pub fn build_platform_intelligence(ctx: &AppContext) -> PlatformIntelligence { let summary = match verdict { PreflightVerdict::Ready => format!( - "{os_pretty_name} looks ready for pyenv-native runtime installs via {install_strategy}." + "{os_pretty_name} looks ready for pyenv-native runtime installs via {install_strategy}. Shell PATH and shim health are reported in the shell cards and doctor section below." ), PreflightVerdict::NeedsAttention => format!( - "{os_pretty_name} can mostly install runtimes via {install_strategy}, but some optional prerequisites need attention." + "{os_pretty_name} can mostly install runtimes via {install_strategy}, but some install prerequisites need attention." ), PreflightVerdict::Blocked => format!( "{os_pretty_name} is not ready for a successful source/runtime install yet. Resolve blocking prerequisites first." @@ -196,25 +202,6 @@ pub fn build_platform_intelligence(ctx: &AppContext) -> PlatformIntelligence { } } -fn is_install_blocker(name: &str) -> bool { - matches!( - name, - "source-build-shell" - | "source-build-make" - | "source-build-compiler" - | "source-build-readiness" - | "macos-xcode-clt" - | "macos-openssl" - | "termux-tool-clang" - | "termux-tool-make" - | "termux-tool-pkg-config" - | "termux-lib-openssl" - | "termux-lib-libffi" - | "android-termux-prefix" - | "android-source-build-readiness" - ) -} - fn describe_install_strategy(os: &str) -> String { match os { "windows" => "windows NuGet / embeddable packages (no local CPython compile)".to_string(), @@ -241,7 +228,15 @@ fn detect_os_pretty_name(os: &str) -> String { format!("{product} {version}") } } - "windows" => env::var("OS").unwrap_or_else(|_| "Windows".to_string()), + "windows" => { + // %OS% is usually the opaque "Windows_NT"; prefer a human host label. + let product = env::var("OS").unwrap_or_else(|_| "Windows".to_string()); + if product.eq_ignore_ascii_case("Windows_NT") || product.is_empty() { + format!("Windows ({})", env::consts::ARCH) + } else { + product + } + } "android" => { let release = read_command_line(&["getprop", "ro.build.version.release"]) .unwrap_or_else(|| "Android".to_string()); @@ -294,4 +289,12 @@ mod tests { assert!(strategy.contains("source")); assert!(strategy.to_ascii_lowercase().contains("openssl")); } + + #[test] + fn windows_strategy_is_prebuilt_not_source() { + let strategy = describe_install_strategy("windows"); + let lower = strategy.to_ascii_lowercase(); + assert!(lower.contains("nuget") || lower.contains("embeddable")); + assert!(lower.contains("no local cpython compile") || !lower.contains("source build")); + } } diff --git a/crates/pyenv-core/src/preflight/tests.rs b/crates/pyenv-core/src/preflight/tests.rs index db2f91e..101720b 100644 --- a/crates/pyenv-core/src/preflight/tests.rs +++ b/crates/pyenv-core/src/preflight/tests.rs @@ -69,4 +69,54 @@ mod tests { || check.status == DoctorStatus::Info) ); } + + #[test] + fn host_environment_ignores_shell_path_warns_for_verdict() { + use crate::doctor::{DoctorCheck, DoctorStatus}; + use crate::preflight::{PlatformIntelligence, PreflightVerdict}; + + let checks = vec![ + DoctorCheck { + name: "pyenv-bin-on-path".to_string(), + status: DoctorStatus::Warn, + detail: "bin missing from process PATH".to_string(), + }, + DoctorCheck { + name: "shims-on-path".to_string(), + status: DoctorStatus::Warn, + detail: "shims missing from process PATH".to_string(), + }, + DoctorCheck { + name: "functional-shim-check".to_string(), + status: DoctorStatus::Warn, + detail: "python shim not found".to_string(), + }, + DoctorCheck { + name: "selected-version".to_string(), + status: DoctorStatus::Warn, + detail: "missing version".to_string(), + }, + ]; + assert_eq!( + PlatformIntelligence::derive_verdict(&checks, &[]), + PreflightVerdict::Ready, + "shell/shim/selection warns must not mark Host Environment Needs Attention" + ); + } + + #[test] + fn host_environment_marks_attention_for_install_conflicts() { + use crate::doctor::{DoctorCheck, DoctorStatus}; + use crate::preflight::{PlatformIntelligence, PreflightVerdict}; + + let checks = vec![DoctorCheck { + name: "pyenv-win-path-conflict".to_string(), + status: DoctorStatus::Warn, + detail: "legacy pyenv-win shadows native bin".to_string(), + }]; + assert_eq!( + PlatformIntelligence::derive_verdict(&checks, &[]), + PreflightVerdict::NeedsAttention + ); + } } diff --git a/crates/pyenv-core/src/preflight/types.rs b/crates/pyenv-core/src/preflight/types.rs index 46e9917..f17aab6 100644 --- a/crates/pyenv-core/src/preflight/types.rs +++ b/crates/pyenv-core/src/preflight/types.rs @@ -61,17 +61,21 @@ impl PlatformIntelligence { { return PreflightVerdict::Blocked; } - if checks - .iter() - .any(|check| check.status == DoctorStatus::Warn) - { + // Host Environment is install-readiness, not live shell/shim health. + // PATH / shim / selected-version warnings belong in doctor + shell cards — + // they must not mark a healthy Windows NuGet host as "Needs attention" + // merely because a desktop GUI process did not inherit User PATH. + if checks.iter().any(|check| { + check.status == DoctorStatus::Warn && affects_install_readiness(&check.name) + }) { return PreflightVerdict::NeedsAttention; } PreflightVerdict::Ready } } -fn is_blocking_check(name: &str) -> bool { +/// Checks that hard-block runtime installs when Warn. +pub(crate) fn is_blocking_check(name: &str) -> bool { matches!( name, "source-build-shell" @@ -89,3 +93,13 @@ fn is_blocking_check(name: &str) -> bool { | "android-source-build-readiness" ) } + +/// Soft install/toolchain prerequisites and install conflicts. +/// Excludes shell PATH, shim function, and selection health (shown elsewhere). +pub(crate) fn affects_install_readiness(name: &str) -> bool { + is_blocking_check(name) + || matches!( + name, + "root-directory" | "pyenv-win-root" | "pyenv-win-path-conflict" + ) +} diff --git a/crates/pyenv-core/src/runtime/tests.rs b/crates/pyenv-core/src/runtime/tests.rs index 0f928ea..1f5bbcc 100644 --- a/crates/pyenv-core/src/runtime/tests.rs +++ b/crates/pyenv-core/src/runtime/tests.rs @@ -14,9 +14,11 @@ mod tests { use super::super::{ BASE_VENV_DIR_NAME, collect_shim_names_from_prefix, find_command_in_prefix, inventory_roots_for_version, managed_search_roots_for_version, prefix_bin_dirs, - search_path_entries, }; + #[cfg(windows)] + use super::super::search_path_entries; + fn test_path_ext() -> Option { if cfg!(windows) { Some(OsString::from(".exe;.bat;.cmd")) diff --git a/crates/pyenv-core/src/shell/tests.rs b/crates/pyenv-core/src/shell/tests.rs index e40efc2..9559b0b 100644 --- a/crates/pyenv-core/src/shell/tests.rs +++ b/crates/pyenv-core/src/shell/tests.rs @@ -234,16 +234,27 @@ fn init_print_for_pwsh_sets_path_env_and_function() { assert!(report.stdout.iter().any(|line| { line.contains("Invoke-PyenvPassthrough $pyenvExe (@([string]$command) + @($arguments))") })); - assert!(report.stdout.iter().any(|line| { - line.contains("$_ -in @('init', 'virtualenv-init')") - })); - assert!(report.stdout.iter().any(|line| { - line.contains("if ($output.Count -gt 0) { $output }") - })); + assert!( + report + .stdout + .iter() + .any(|line| { line.contains("$_ -in @('init', 'virtualenv-init')") }) + ); + assert!( + report + .stdout + .iter() + .any(|line| { line.contains("if ($output.Count -gt 0) { $output }") }) + ); assert!(report.stdout.iter().any(|line| { line.contains("Invoke-PyenvCaptured $pyenvExe (@('sh-shell', '--') + @($arguments))") })); - assert!(report.stdout.iter().any(|line| line.contains("Invoke-PyenvExpression"))); + assert!( + report + .stdout + .iter() + .any(|line| line.contains("Invoke-PyenvExpression")) + ); assert!(report.stdout.iter().any(|line| line.contains("sh-shell"))); assert!( report diff --git a/crates/pyenv-gui/tauri.conf.json b/crates/pyenv-gui/tauri.conf.json index 9b96768..3d55f60 100644 --- a/crates/pyenv-gui/tauri.conf.json +++ b/crates/pyenv-gui/tauri.conf.json @@ -1,6 +1,6 @@ { "productName": "Pyenv Native", - "version": "0.2.36", + "version": "0.2.37", "identifier": "com.pyenv-native.gui", "build": { "frontendDist": "ui" diff --git a/crates/pyenv-gui/ui/app.js b/crates/pyenv-gui/ui/app.js index c448cf2..c9e989c 100644 --- a/crates/pyenv-gui/ui/app.js +++ b/crates/pyenv-gui/ui/app.js @@ -2448,19 +2448,34 @@ async function loadPlatformIntelligence() { if (blockersEl) { const blockers = intel.blocking_issues || []; - if (blockers.length) { + const warnings = intel.warnings || []; + if (blockers.length || warnings.length) { blockersEl.style.display = 'block'; blockersEl.replaceChildren(); - const title = document.createElement('div'); - title.style.cssText = 'font-size: 11px; font-weight: 600; color: #f87171; margin-bottom: 6px;'; - title.textContent = 'Blocking before install'; - blockersEl.appendChild(title); - blockers.forEach((issue) => { - const row = document.createElement('div'); - row.style.cssText = 'font-size: 11px; color: var(--text-muted); line-height: 1.4; margin-bottom: 4px;'; - row.textContent = `• ${issue}`; - blockersEl.appendChild(row); - }); + if (blockers.length) { + const title = document.createElement('div'); + title.style.cssText = 'font-size: 11px; font-weight: 600; color: #f87171; margin-bottom: 6px;'; + title.textContent = 'Blocking before install'; + blockersEl.appendChild(title); + blockers.forEach((issue) => { + const row = document.createElement('div'); + row.style.cssText = 'font-size: 11px; color: var(--text-muted); line-height: 1.4; margin-bottom: 4px;'; + row.textContent = `• ${issue}`; + blockersEl.appendChild(row); + }); + } + if (warnings.length) { + const warnTitle = document.createElement('div'); + warnTitle.style.cssText = `font-size: 11px; font-weight: 600; color: #fbbf24; margin-bottom: 6px;${blockers.length ? ' margin-top: 10px;' : ''}`; + warnTitle.textContent = 'Install prerequisites needing attention'; + blockersEl.appendChild(warnTitle); + warnings.forEach((issue) => { + const row = document.createElement('div'); + row.style.cssText = 'font-size: 11px; color: var(--text-muted); line-height: 1.4; margin-bottom: 4px;'; + row.textContent = `• ${issue}`; + blockersEl.appendChild(row); + }); + } } else { blockersEl.style.display = 'none'; blockersEl.replaceChildren(); diff --git a/crates/pyenv-mcp/Cargo.toml b/crates/pyenv-mcp/Cargo.toml index b09249a..c865c8a 100644 --- a/crates/pyenv-mcp/Cargo.toml +++ b/crates/pyenv-mcp/Cargo.toml @@ -6,9 +6,9 @@ license.workspace = true [dependencies] anyhow = "^1.0.104" -clap = { version = "^4.6.4", features = ["derive"] } +clap = { version = "^4.6.6", features = ["derive"] } pyenv-core = { path = "../pyenv-core" } -rmcp = { version = "^2.2.0", features = ["transport-io"] } +rmcp = { version = "^3.1.2", features = ["transport-io"] } schemars = "^1.2.2" serde = { version = "^1.0.229", features = ["derive"] } serde_json = "^1.0.151" diff --git a/python-package/pyproject.toml b/python-package/pyproject.toml index c4a26fe..6d6697c 100644 --- a/python-package/pyproject.toml +++ b/python-package/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "hatchling.build" [project] name = "pyenv-native" -version = "0.2.36" +version = "0.2.37" description = "Python install package for the native-first pyenv-native runtime bundles." readme = "README.md" requires-python = ">=3.8" diff --git a/python-package/src/pyenv_native_bootstrap/__init__.py b/python-package/src/pyenv_native_bootstrap/__init__.py index d2bd6a6..ac0130c 100644 --- a/python-package/src/pyenv_native_bootstrap/__init__.py +++ b/python-package/src/pyenv_native_bootstrap/__init__.py @@ -3,4 +3,4 @@ __all__ = ["__version__"] -__version__ = "0.2.36" \ No newline at end of file +__version__ = "0.2.37" \ No newline at end of file diff --git a/scripts/gui-a11y/package-lock.json b/scripts/gui-a11y/package-lock.json index 9480698..94c7af4 100644 --- a/scripts/gui-a11y/package-lock.json +++ b/scripts/gui-a11y/package-lock.json @@ -6,27 +6,57 @@ "": { "name": "pyenv-native-gui-a11y", "dependencies": { - "axe-core": "^4.10.3", - "jsdom": "^26.1.0" + "axe-core": "^4.13.0", + "jsdom": "^30.0.1" } }, "node_modules/@asamuzakjp/css-color": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-3.2.0.tgz", - "integrity": "sha512-K1A6z8tS3XsmCMM86xoWdn7Fkdn9m6RSVtocUrJYIwZnFVkng/PvkEoWtOWmP+Scc6saYWHWZYbndEEXxl24jw==", + "version": "6.0.7", + "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-6.0.7.tgz", + "integrity": "sha512-vC/bk1Lz7Tn/EfU9/apOTBk80/8dyGyWMowPoV1tJ52muDGsDqt2HPT2klrFUiY60MQmQv9q8yIht15JnBgDGw==", "license": "MIT", "dependencies": { - "@csstools/css-calc": "^2.1.3", - "@csstools/css-color-parser": "^3.0.9", - "@csstools/css-parser-algorithms": "^3.0.4", - "@csstools/css-tokenizer": "^3.0.3", - "lru-cache": "^10.4.3" + "@csstools/css-calc": "^3.3.0", + "@csstools/css-color-parser": "^4.1.10", + "@csstools/css-parser-algorithms": "^4.0.0", + "@csstools/css-tokenizer": "^4.0.0", + "lru-cache": "^11.5.2" + }, + "engines": { + "node": "^22.13.0 || >=24.0.0" + } + }, + "node_modules/@asamuzakjp/dom-selector": { + "version": "8.3.2", + "resolved": "https://registry.npmjs.org/@asamuzakjp/dom-selector/-/dom-selector-8.3.2.tgz", + "integrity": "sha512-93Z1N+BQNXysodoicpOIyNh2drHfz/CTf9nnT0FEx72GJcIiwgydD7tGAr78j41LsYn3hlRn+LdGPuBLn1Bl8Q==", + "license": "MIT", + "dependencies": { + "bidi-js": "^1.0.3", + "css-tree": "^3.2.1", + "is-potential-custom-element-name": "^1.0.1", + "lru-cache": "^11.5.2" + }, + "engines": { + "node": "^22.13.0 || >=24.0.0" + } + }, + "node_modules/@bramus/specificity": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/@bramus/specificity/-/specificity-2.4.2.tgz", + "integrity": "sha512-ctxtJ/eA+t+6q2++vj5j7FYX3nRu311q1wfYH3xjlLOsczhlhxAg2FWNUXhpGvAw3BWo1xBcvOV6/YLc2r5FJw==", + "license": "MIT", + "dependencies": { + "css-tree": "^3.0.0" + }, + "bin": { + "specificity": "bin/cli.js" } }, "node_modules/@csstools/color-helpers": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-5.1.0.tgz", - "integrity": "sha512-S11EXWJyy0Mz5SYvRmY8nJYTFFd1LCNV+7cXyAgQtOOuzb4EsgfqDufL+9esx72/eLhsRdGZwaldu/h+E4t4BA==", + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-6.1.0.tgz", + "integrity": "sha512-064IFJdjTfUqnjpCVpMOdbr8FLQBhinbZj6yRv2An2E41O/pLEXqfFRWqGq/SxlE5PEUYTlvWsG2r8MswAVvkg==", "funding": [ { "type": "github", @@ -39,13 +69,13 @@ ], "license": "MIT-0", "engines": { - "node": ">=18" + "node": ">=20.19.0" } }, "node_modules/@csstools/css-calc": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-2.1.4.tgz", - "integrity": "sha512-3N8oaj+0juUw/1H3YwmDDJXCgTB1gKU6Hc/bB502u9zR0q2vd786XJH9QfrKIEgFlZmhZiq6epXl4rHqhzsIgQ==", + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-3.3.0.tgz", + "integrity": "sha512-c5ihYsPkdG6JCkU2zTMm4+k6r7RXuGxtWYhu5DHMIiF1FHzrfmHL5so11AoFpUv/tu61xfcmT4AmKoFfMPoqdQ==", "funding": [ { "type": "github", @@ -58,17 +88,17 @@ ], "license": "MIT", "engines": { - "node": ">=18" + "node": ">=20.19.0" }, "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.5", - "@csstools/css-tokenizer": "^3.0.4" + "@csstools/css-parser-algorithms": "^4.0.0", + "@csstools/css-tokenizer": "^4.0.0" } }, "node_modules/@csstools/css-color-parser": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-3.1.0.tgz", - "integrity": "sha512-nbtKwh3a6xNVIp/VRuXV64yTKnb1IjTAEEh3irzS+HkKjAOYLTGNb9pmVNntZ8iVBHcWDA2Dof0QtPgFI1BaTA==", + "version": "4.1.10", + "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-4.1.10.tgz", + "integrity": "sha512-UZhQLIUyJaaMepqehrCODwCg2KW25vFvLWBmqYFaPclYvvxzj/sG8LBOhBFCp11i9uE7t1EyS+RAoV9tztPFyw==", "funding": [ { "type": "github", @@ -81,21 +111,21 @@ ], "license": "MIT", "dependencies": { - "@csstools/color-helpers": "^5.1.0", - "@csstools/css-calc": "^2.1.4" + "@csstools/color-helpers": "^6.1.0", + "@csstools/css-calc": "^3.3.0" }, "engines": { - "node": ">=18" + "node": ">=20.19.0" }, "peerDependencies": { - "@csstools/css-parser-algorithms": "^3.0.5", - "@csstools/css-tokenizer": "^3.0.4" + "@csstools/css-parser-algorithms": "^4.0.0", + "@csstools/css-tokenizer": "^4.0.0" } }, "node_modules/@csstools/css-parser-algorithms": { - "version": "3.0.5", - "resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-3.0.5.tgz", - "integrity": "sha512-DaDeUkXZKjdGhgYaHNJTV9pV7Y9B3b644jCLs9Upc3VeNGg6LWARAT6O+Q+/COo+2gg/bM5rhpMAtf70WqfBdQ==", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-4.0.0.tgz", + "integrity": "sha512-+B87qS7fIG3L5h3qwJ/IFbjoVoOe/bpOdh9hAjXbvx0o8ImEmUsGXN0inFOnk2ChCFgqkkGFQ+TpM5rbhkKe4w==", "funding": [ { "type": "github", @@ -108,16 +138,40 @@ ], "license": "MIT", "engines": { - "node": ">=18" + "node": ">=20.19.0" }, "peerDependencies": { - "@csstools/css-tokenizer": "^3.0.4" + "@csstools/css-tokenizer": "^4.0.0" + } + }, + "node_modules/@csstools/css-syntax-patches-for-csstree": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.1.7.tgz", + "integrity": "sha512-fQ+05118eQS1cofO3aJpB5efgpBZMvIzwr/sbC8kDLVA5XLG8q1kJV5yzrUAI1f7lvhPnm8fgIjzFB8/O/5Dig==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/csstools" + }, + { + "type": "opencollective", + "url": "https://opencollective.com/csstools" + } + ], + "license": "MIT-0", + "peerDependencies": { + "css-tree": "^3.2.1" + }, + "peerDependenciesMeta": { + "css-tree": { + "optional": true + } } }, "node_modules/@csstools/css-tokenizer": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-3.0.4.tgz", - "integrity": "sha512-Vd/9EVDiu6PPJt9yAh6roZP6El1xHrdvIVGjyBsHR0RYwNHgL7FJPyIIW4fANJNG6FtyZfvlRPpFI4ZM/lubvw==", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-4.0.0.tgz", + "integrity": "sha512-QxULHAm7cNu72w97JUNCBFODFaXpbDg+dP8b/oWFAZ2MTRppA3U00Y2L1HqaS4J6yBqxwa/Y3nMBaxVKbB/NsA==", "funding": [ { "type": "github", @@ -130,68 +184,82 @@ ], "license": "MIT", "engines": { - "node": ">=18" + "node": ">=20.19.0" } }, - "node_modules/agent-base": { - "version": "7.1.4", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.4.tgz", - "integrity": "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ==", + "node_modules/@exodus/bytes": { + "version": "1.15.1", + "resolved": "https://registry.npmjs.org/@exodus/bytes/-/bytes-1.15.1.tgz", + "integrity": "sha512-S6mL0yNB/Abt9Ei4tq8gDhcczc4S3+vQ4ra7vxnAf+YHC02srtqxKKZghx2Dq6p0e66THKwR6r8N6P95wEty7Q==", "license": "MIT", "engines": { - "node": ">= 14" + "node": "^20.19.0 || ^22.12.0 || >=24.0.0" + }, + "peerDependencies": { + "@noble/hashes": "^1.8.0 || ^2.0.0" + }, + "peerDependenciesMeta": { + "@noble/hashes": { + "optional": true + } } }, "node_modules/axe-core": { - "version": "4.12.1", - "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.12.1.tgz", - "integrity": "sha512-s7iGf5GaVMxEG0ENN9x+xTr7GFZCb1ZP/1uATUpCEK2X78nDB3RwbtFCo9pGAf9ru+VwoQ464DkaLEeRM08wJA==", + "version": "4.13.0", + "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.13.0.tgz", + "integrity": "sha512-UzGt8zg7Ny8djbYMhxl2zuEevVa7r2gJjYY5Lwr1xM7+XU2nd6CkIWFTVcCIbAP63vSz71NaVyyuSk9lHKcy0A==", "license": "MPL-2.0", "engines": { "node": ">=4" } }, - "node_modules/cssstyle": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.6.0.tgz", - "integrity": "sha512-2z+rWdzbbSZv6/rhtvzvqeZQHrBaqgogqt85sqFNbabZOuFbCVFb8kPeEtZjiKkbrm395irpNKiYeFeLiQnFPg==", + "node_modules/bidi-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/bidi-js/-/bidi-js-1.0.3.tgz", + "integrity": "sha512-RKshQI1R3YQ+n9YJz2QQ147P66ELpa1FQEg20Dk8oW9t2KgLbpDLLp9aGZ7y8WHSshDknG0bknqGw5/tyCs5tw==", + "license": "MIT", + "dependencies": { + "require-from-string": "^2.0.2" + } + }, + "node_modules/css-tree": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-3.2.1.tgz", + "integrity": "sha512-X7sjQzceUhu1u7Y/ylrRZFU2FS6LRiFVp6rKLPg23y3x3c3DOKAwuXGDp+PAGjh6CSnCjYeAul8pcT8bAl+lSA==", "license": "MIT", "dependencies": { - "@asamuzakjp/css-color": "^3.2.0", - "rrweb-cssom": "^0.8.0" + "mdn-data": "2.27.1", + "source-map-js": "^1.2.1" }, "engines": { - "node": ">=18" + "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0" } }, "node_modules/data-urls": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-5.0.0.tgz", - "integrity": "sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==", + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-7.0.0.tgz", + "integrity": "sha512-23XHcCF+coGYevirZceTVD7NdJOqVn+49IHyxgszm+JIiHLoB2TkmPtsYkNWT1pvRSGkc35L6NHs0yHkN2SumA==", "license": "MIT", "dependencies": { - "whatwg-mimetype": "^4.0.0", - "whatwg-url": "^14.0.0" + "whatwg-mimetype": "^5.0.0", + "whatwg-url": "^16.0.0" }, "engines": { - "node": ">=18" + "node": "^20.19.0 || ^22.12.0 || >=24.0.0" } }, - "node_modules/debug": { - "version": "4.4.3", - "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz", - "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==", + "node_modules/data-urls/node_modules/whatwg-url": { + "version": "16.0.1", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-16.0.1.tgz", + "integrity": "sha512-1to4zXBxmXHV3IiSSEInrreIlu02vUOvrhxJJH5vcxYTBDAx51cqZiKdyTxlecdKNSjj8EcxGBxNf6Vg+945gw==", "license": "MIT", "dependencies": { - "ms": "^2.1.3" + "@exodus/bytes": "^1.11.0", + "tr46": "^6.0.0", + "webidl-conversions": "^8.0.1" }, "engines": { - "node": ">=6.0" - }, - "peerDependenciesMeta": { - "supports-color": { - "optional": true - } + "node": "^20.19.0 || ^22.12.0 || >=24.0.0" } }, "node_modules/decimal.js": { @@ -201,65 +269,27 @@ "license": "MIT" }, "node_modules/entities": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", - "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-8.0.0.tgz", + "integrity": "sha512-zwfzJecQ/Uej6tusMqwAqU/6KL2XaB2VZ2Jg54Je6ahNBGNH6Ek6g3jjNCF0fG9EWQKGZNddNjU5F1ZQn/sBnA==", "license": "BSD-2-Clause", "engines": { - "node": ">=0.12" + "node": ">=20.19.0" }, "funding": { "url": "https://github.com/fb55/entities?sponsor=1" } }, "node_modules/html-encoding-sniffer": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-4.0.0.tgz", - "integrity": "sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==", - "license": "MIT", - "dependencies": { - "whatwg-encoding": "^3.1.1" - }, - "engines": { - "node": ">=18" - } - }, - "node_modules/http-proxy-agent": { - "version": "7.0.2", - "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-7.0.2.tgz", - "integrity": "sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==", - "license": "MIT", - "dependencies": { - "agent-base": "^7.1.0", - "debug": "^4.3.4" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/https-proxy-agent": { - "version": "7.0.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz", - "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==", - "license": "MIT", - "dependencies": { - "agent-base": "^7.1.2", - "debug": "4" - }, - "engines": { - "node": ">= 14" - } - }, - "node_modules/iconv-lite": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", - "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-6.0.0.tgz", + "integrity": "sha512-CV9TW3Y3f8/wT0BRFc1/KAVQ3TUHiXmaAb6VW9vtiMFf7SLoMd1PdAc4W3KFOFETBJUb90KatHqlsZMWV+R9Gg==", "license": "MIT", "dependencies": { - "safer-buffer": ">= 2.1.2 < 3.0.0" + "@exodus/bytes": "^1.6.0" }, "engines": { - "node": ">=0.10.0" + "node": "^20.19.0 || ^22.12.0 || >=24.0.0" } }, "node_modules/is-potential-custom-element-name": { @@ -269,37 +299,38 @@ "license": "MIT" }, "node_modules/jsdom": { - "version": "26.1.0", - "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-26.1.0.tgz", - "integrity": "sha512-Cvc9WUhxSMEo4McES3P7oK3QaXldCfNWp7pl2NNeiIFlCoLr3kfq9kb1fxftiwk1FLV7CvpvDfonxtzUDeSOPg==", + "version": "30.0.1", + "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-30.0.1.tgz", + "integrity": "sha512-52v7mUVUfNQVYYqE1lcdaymWL0njO7lTLUog6ZvW2U5KsbiLk/GnZlVJ+qx0xfNJZ6Gn+KSpPNE52vurbxZwrA==", "license": "MIT", "dependencies": { - "cssstyle": "^4.2.1", - "data-urls": "^5.0.0", - "decimal.js": "^10.5.0", - "html-encoding-sniffer": "^4.0.0", - "http-proxy-agent": "^7.0.2", - "https-proxy-agent": "^7.0.6", + "@asamuzakjp/css-color": "^6.0.5", + "@asamuzakjp/dom-selector": "^8.3.0", + "@bramus/specificity": "^2.4.2", + "@csstools/css-syntax-patches-for-csstree": "^1.1.7", + "@exodus/bytes": "^1.15.1", + "css-tree": "^3.2.1", + "data-urls": "^7.0.0", + "decimal.js": "^10.6.0", + "html-encoding-sniffer": "^6.0.0", "is-potential-custom-element-name": "^1.0.1", - "nwsapi": "^2.2.16", - "parse5": "^7.2.1", - "rrweb-cssom": "^0.8.0", + "lru-cache": "^11.5.2", + "parse5": "^8.0.1", "saxes": "^6.0.0", "symbol-tree": "^3.2.4", - "tough-cookie": "^5.1.1", + "tough-cookie": "^6.0.2", + "undici": "^8.9.0", "w3c-xmlserializer": "^5.0.0", - "webidl-conversions": "^7.0.0", - "whatwg-encoding": "^3.1.1", - "whatwg-mimetype": "^4.0.0", - "whatwg-url": "^14.1.1", - "ws": "^8.18.0", + "webidl-conversions": "^8.0.1", + "whatwg-mimetype": "^5.0.0", + "whatwg-url": "^17.1.0", "xml-name-validator": "^5.0.0" }, "engines": { - "node": ">=18" + "node": "^22.22.2 || ^24.15.0 || >=26.0.0" }, "peerDependencies": { - "canvas": "^3.0.0" + "canvas": "^3.2.3" }, "peerDependenciesMeta": { "canvas": { @@ -308,30 +339,27 @@ } }, "node_modules/lru-cache": { - "version": "10.4.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz", - "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==", - "license": "ISC" - }, - "node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "license": "MIT" + "version": "11.5.2", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.5.2.tgz", + "integrity": "sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g==", + "license": "BlueOak-1.0.0", + "engines": { + "node": "20 || >=22" + } }, - "node_modules/nwsapi": { - "version": "2.2.24", - "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.2.24.tgz", - "integrity": "sha512-7YRhZ3jS45LwmSCT4b2sVFHt/WuovaktDU07QrtOBY2PXskss5a9jfmR9jptyumwXST+rFjrmppMY1KT/yn35A==", - "license": "MIT" + "node_modules/mdn-data": { + "version": "2.27.1", + "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.27.1.tgz", + "integrity": "sha512-9Yubnt3e8A0OKwxYSXyhLymGW4sCufcLG6VdiDdUGVkPhpqLxlvP5vl1983gQjJl3tqbrM731mjaZaP68AgosQ==", + "license": "CC0-1.0" }, "node_modules/parse5": { - "version": "7.3.0", - "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.3.0.tgz", - "integrity": "sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==", + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-8.0.1.tgz", + "integrity": "sha512-z1e/HMG90obSGeidlli3hj7cbocou0/wa5HacvI3ASx34PecNjNQeaHNo5WIZpWofN9kgkqV1q5YvXe3F0FoPw==", "license": "MIT", "dependencies": { - "entities": "^6.0.0" + "entities": "^8.0.0" }, "funding": { "url": "https://github.com/inikulin/parse5?sponsor=1" @@ -346,17 +374,14 @@ "node": ">=6" } }, - "node_modules/rrweb-cssom": { - "version": "0.8.0", - "resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.8.0.tgz", - "integrity": "sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==", - "license": "MIT" - }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "license": "MIT" + "node_modules/require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } }, "node_modules/saxes": { "version": "6.0.0", @@ -370,6 +395,15 @@ "node": ">=v12.22.7" } }, + "node_modules/source-map-js": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz", + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/symbol-tree": { "version": "3.2.4", "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz", @@ -377,45 +411,54 @@ "license": "MIT" }, "node_modules/tldts": { - "version": "6.1.86", - "resolved": "https://registry.npmjs.org/tldts/-/tldts-6.1.86.tgz", - "integrity": "sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==", + "version": "7.4.10", + "resolved": "https://registry.npmjs.org/tldts/-/tldts-7.4.10.tgz", + "integrity": "sha512-GgouD1B+sWwvkaEq8vXC15DjQitxbvs12oIXELpconwm+Tg3zfcEv4jgzq3vtKverDXsg3VI8aRgNL2Nra0Iog==", "license": "MIT", "dependencies": { - "tldts-core": "^6.1.86" + "tldts-core": "^7.4.10" }, "bin": { "tldts": "bin/cli.js" } }, "node_modules/tldts-core": { - "version": "6.1.86", - "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-6.1.86.tgz", - "integrity": "sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==", + "version": "7.4.10", + "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-7.4.10.tgz", + "integrity": "sha512-KnQjp53ZekKgm/r3l+u8kJGGzYgrWdP8+Mql7a4vijh2WE0IrZWspQj/TpTxDho/YxO+AnOZnIjQcCD+q6iJsw==", "license": "MIT" }, "node_modules/tough-cookie": { - "version": "5.1.2", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-5.1.2.tgz", - "integrity": "sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==", + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-6.0.2.tgz", + "integrity": "sha512-exgYmnmL/sJpR3upZfXG5PoatXQii55xAiXGXzY+sROLZ/Y+SLcp9PgJNI9Vz37HpQ74WvDcLT8eqm+kV3FzrA==", "license": "BSD-3-Clause", "dependencies": { - "tldts": "^6.1.32" + "tldts": "^7.0.5" }, "engines": { "node": ">=16" } }, "node_modules/tr46": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-5.1.1.tgz", - "integrity": "sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==", + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-6.0.0.tgz", + "integrity": "sha512-bLVMLPtstlZ4iMQHpFHTR7GAGj2jxi8Dg0s2h2MafAE4uSWF98FC/3MomU51iQAMf8/qDUbKWf5GxuvvVcXEhw==", "license": "MIT", "dependencies": { "punycode": "^2.3.1" }, "engines": { - "node": ">=18" + "node": ">=20" + } + }, + "node_modules/undici": { + "version": "8.10.0", + "resolved": "https://registry.npmjs.org/undici/-/undici-8.10.0.tgz", + "integrity": "sha512-HvltHd7avK13QIw/oLe4qoOLyoVSoafqJ2jYOrtMRBkbYT31eiBQ8O0ehRKZiEZCMEyLFQNIADpgCWC5fALvYQ==", + "license": "MIT", + "engines": { + "node": ">=22.19.0" } }, "node_modules/w3c-xmlserializer": { @@ -431,68 +474,35 @@ } }, "node_modules/webidl-conversions": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz", - "integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==", + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-8.0.1.tgz", + "integrity": "sha512-BMhLD/Sw+GbJC21C/UgyaZX41nPt8bUTg+jWyDeg7e7YN4xOM05YPSIXceACnXVtqyEw/LMClUQMtMZ+PGGpqQ==", "license": "BSD-2-Clause", "engines": { - "node": ">=12" - } - }, - "node_modules/whatwg-encoding": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz", - "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==", - "deprecated": "Use @exodus/bytes instead for a more spec-conformant and faster implementation", - "license": "MIT", - "dependencies": { - "iconv-lite": "0.6.3" - }, - "engines": { - "node": ">=18" + "node": ">=20" } }, "node_modules/whatwg-mimetype": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz", - "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==", + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-5.0.0.tgz", + "integrity": "sha512-sXcNcHOC51uPGF0P/D4NVtrkjSU2fNsm9iog4ZvZJsL3rjoDAzXZhkm2MWt1y+PUdggKAYVoMAIYcs78wJ51Cw==", "license": "MIT", "engines": { - "node": ">=18" + "node": ">=20" } }, "node_modules/whatwg-url": { - "version": "14.2.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.2.0.tgz", - "integrity": "sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==", + "version": "17.1.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-17.1.0.tgz", + "integrity": "sha512-3GeworPmc2ZfEEHP7lEbUfBX/L75wdEsi0rLNhXcXxnoN5jyq0SL5gCy06SGW2cyTIZdTvWIDQNQoza++vKeaw==", "license": "MIT", "dependencies": { - "tr46": "^5.1.0", - "webidl-conversions": "^7.0.0" + "@exodus/bytes": "^1.15.1", + "tr46": "^6.0.0", + "webidl-conversions": "^8.0.1" }, "engines": { - "node": ">=18" - } - }, - "node_modules/ws": { - "version": "8.21.0", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.21.0.tgz", - "integrity": "sha512-Vsp28b7DRcimFQvrqu2Wek3z1iYxDCWqHYB8Qsnk/S4RfaCQzPGPyBNuVjJV3cd6UiKtUtp6sNM77gWvzcCH+g==", - "license": "MIT", - "engines": { - "node": ">=10.0.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": ">=5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } + "node": "^22.14.0 || >=24.0.0" } }, "node_modules/xml-name-validator": { diff --git a/scripts/gui-a11y/package.json b/scripts/gui-a11y/package.json index 7c851cd..db1d22e 100644 --- a/scripts/gui-a11y/package.json +++ b/scripts/gui-a11y/package.json @@ -6,7 +6,7 @@ "check": "node check-a11y.mjs" }, "dependencies": { - "axe-core": "^4.10.3", - "jsdom": "^26.1.0" + "axe-core": "^4.13.0", + "jsdom": "^30.0.1" } }