Repository navigation
Fix uv project with no env falling back to system Python (#964) - #965
Open
Mikola Lysenko (mikolalysenko) wants to merge 5 commits into
Open
Mikola Lysenko (mikolalysenko) wants to merge 5 commits into
Mikola Lysenko (mikolalysenko) wants to merge 5 commits into
Conversation
Assisted-by: Claude Code:claude-opus-5-5
A fresh uv checkout (uv.lock with no .venv synced yet, or a UV_PROJECT_ENVIRONMENT that doesn't exist yet) and a directory holding only PEP 723 script locks fell back to the global site-packages. Every OS-Python package then joined the candidate set, so a vendored scan tried to vendor packages the project never depends on and exited 1 with pypi_uv_lock_package_missing. uv only ever installs such a project into its own env, and the lock already supplies the lock-only packages, so the crawl now returns no env for it. A uv.lock shared with Poetry, PDM or Pipenv files keeps the old fallback. Fixes #964 Assisted-by: Claude Code:claude-opus-5-5
main's coverage job is red: the digest guard test from #865 requires production hashing to go through the utils::digest helpers, and the Gradle code from #646 still hashes inline. This is the same change as #878, ported so this PR's CI can go green; it no-ops once #878 lands. Assisted-by: Claude Code:claude-opus-5-5
Collaborator
Author
|
[agent] CI notes on the earlier heads:
Generated by Claude Code |
Mikola Lysenko (mikolalysenko)
marked this pull request as ready for review
October 6, 2026 22:05
Collaborator
Author
|
BugBot review Generated by Claude Code |
661c117 ran `cargo fmt --all`, which reformatted 118 files the uv fix never changes. main isn't rustfmt-clean and CI doesn't check formatting, so the sweep adds nothing. It also hides the real change and conflicts with every other open PR that touches those files. Each reverted file is byte-identical to rustfmt's output on the merge-base version, so this drops formatting only. The six files that carry the fix and the ported #878 change keep their formatting. Co-Authored-By: Claude <noreply@anthropic.com>
Collaborator
Author
|
bugbot run Generated by Claude Code |
Tanmay Singla (Tanmay182003)
approved these changes
Oct 7, 2026
Collaborator
Author
|
[burn-down agent] Ready for review at
Generated by Claude Code |
Conflict in crates/socket-patch-core/src/crawlers/python_crawler.rs: main (#950) added an is_pipenv_project guard and this branch added a uv_owns_project_env guard at the same spot in get_site_packages_paths. Kept both: the Pipenv guard first, then the uv guard, and merged the doc comment to name both. Co-Authored-By: Claude <noreply@anthropic.com>
Collaborator
Author
|
bugbot run Generated by Claude Code |
There was a problem hiding this comment.
✅ Bugbot reviewed your changes and found no new issues!
Comment @cursor review or bugbot run to trigger another review on this PR
Reviewed by Cursor Bugbot for commit c47aa0d. Configure here.
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
LLM Description written by Claude Code:claude-opus-5-5
Fixes #964
Summary
A vendored scan of a fresh uv checkout (
uv.lock, no.venvsynced yet), or of a directory holding only PEP 723 script locks, no longer pulls the system Python's packages into the candidate set. Before this, every OS-Python package with a Socket patch (PyYAML, requests, … on stock Ubuntu runners) madescan --mode vendoredexit 1 withpypi_uv_lock_package_missing, even when nothing the project depends on was patched.Root cause
PythonCrawler::get_site_packages_pathsfalls back toget_global_python_site_packages()whenever the cwd has a Python project marker but no project env was found. A uv project only ever installs into uv's own env (./.venvorUV_PROJECT_ENVIRONMENT), and a script lock's env lives in uv's cache. So with nothing synced yet, nothing is installed for the project, and its lock-only packages already come from the lock (lockfileOnlyPackages).Same root cause as #947 / #504. PR #950 handles the Pipenv half with an
is_pipenv_projectguard at the same spot; this PR adds the uv half. The two touch adjacent lines, so whichever lands second needs a trivial merge.Change
uv_owns_project_env(cwd)is true for auv.lockthat no other manager shares, or a directory whose only Python markers are*.py.lockscript locks. In that case the crawl returns no env instead of falling back.uv.locknext to Poetry / PDM / Pipenv files keeps the old fallback, because Poetry withvirtualenvs.create = falseinstalls into the interpreter it runs on. The "another manager claims this project" check moved out ofuv_project_environment_site_packagesintoclaimed_by_non_uv_manager, so both share it.get_site_packages_paths_falls_back_via_uv_lock_marker, which pinned the buggy behaviour. CLI_CONTRACT's "cwd-only" section already describes the new behaviour.pypi_uv_lock_package_missingremedy text invendor/pypi_uv.rsis unchanged. Without the fallback, a package the project doesn't depend on can't reach it any more.utils::digest).mainis red onproduction_digests_go_through_the_helpers, and the change no-ops once Route Gradle digests through utils::digest #878 lands.cargo fmt --allsweep that had reformatted 118 files this fix doesn't touch. Each reverted file is byte-identical to rustfmt's output on the merge-base version. The diff is now the 6 files listed in the PR.Tests (red → green)
uv.lockalone /pyproject.toml+uv.lock/ unsyncedUV_PROJECT_ENVIRONMENT/tool.py+tool.py.lockcrawler_python_e2e::get_site_packages_paths_uv_without_env_never_falls_back_to_globalin_process_python_envs::uv_fresh_checkout_never_scans_the_system_pythonsystem-decoy@6.6.6reached the batch queryuv.lock+poetry.lockkeeps the fallbackcrawler_python_e2e::get_site_packages_paths_uv_lock_beside_poetry_keeps_fallbackLocal runs
cargo clippy --workspace --all-features -- -D warnings✅ (re-run on 1822d82)crawler_python_e2e(62) andin_process_python_envs(20) ✅ (re-run on 1822d82)cargo test -p socket-patch-core --all-features: all pass except 4 lib tests that inject failures with chmod (copy_tree::relax_loop_must_not_traverse_symlinked_root,vlt_heal::an_unremovable_hidden_lock_keeps_every_store_entry,pypi_poetry::wire_write_failure_…,pypi_requirements::wire_failure_rolls_back_…). They can't fail as uid 0, which is how this container runs, and they pass in CI.in_process_python_envs,e2e_pypi,hosted_superseding_pypi,mode_migration_pypi✅.covgap_commands_vendor: 3 tests that inject state-write failures fail for the same root reason.e2e_vendor_pypi_build -- --include-ignored(uv 0.11.32): 35/35 ✅e2e_redirect_uv_build -- --ignored: 5 ✅. 4 fail because the test binary can't reachhttps://pypi.org/pypi/six/1.16.0/jsonthrough this sandbox's TLS proxy during the upstream restore step, which this diff doesn't touch. CI runs these with real network.cargo test --workspacecan't link within this session's disk allowance, so CI is the full-suite gate.🤖 Generated with Claude Code
https://claude.ai/code/session_012H7zqyRTeMzzAxit6xfV6r
Note
Medium Risk
Changes which Python installs are considered in project-scoped crawls; misclassification could skip real envs or still leak globals, but the guard is narrow and heavily tested.
Overview
Fixes #964: project-scoped scans no longer treat the OS Python as part of a uv-managed tree when uv has not synced an env yet.
PythonCrawler::get_site_packages_pathsused to fall back to globalsite-packageswhenever the cwd looked like a Python project but had no local venv—so a freshuv.lockcheckout (or a PEP 723*.py.lockscript dir) could pull conda/system packages into vendored/agent scans and fail on unrelated patched wheels. The crawler now returns no env paths whenuv_owns_project_envis true (uv.locknot shared with Poetry/PDM/Pipenv, or only*.py.lockmarkers), mirroring the existing Pipenv guard; lockfile-only deps still come from the lock.claimed_by_non_uv_managerwas extracted soUV_PROJECT_ENVIRONMENThandling and the new guard share the same “another manager owns this repo” logic;uv.lock+poetry.lockstill keeps the global fallback for Poetry-on-system-interpreter setups.Tests were flipped/added: e2e asserts empty site-packages (and no global anaconda decoy) for uv/script shapes; CLI asserts
system-decoynever hits the batch API across agent/vendored/hosted modes.Reviewed by Cursor Bugbot for commit c47aa0d. Configure here.