Improve PEP 723 inline-script env setup (failure messages + uv shim fix) - #1764
Merged
Stella Huang (StellaHuang95) merged 2 commits intoSep 4, 2026
Merged
Conversation
Clicking the PEP 723 "Set up environment for this script" CodeLens and having setup produce no environment used to be silent -- the reason was only in the Python Environments output log. The interactive setup command now surfaces an actionable message: - a warning for the no-compatible-python case, with a note when requires-python is an exact two-segment pin like "==3.11" (PEP 440 treats it as exactly 3.11.0, which is often not installable); - a generic "see output" error for other failures; - silence when the user declined the Python install, or when an environment was built but intentionally not associated (the script's metadata changed mid-setup). The env manager records the setup outcome (failed reason or benign skip) on the shared InlineScriptRoutingRegistry as a diagnostic side-channel; the setup command reads it once to choose the message. Only the interactive CodeLens flow shows messages -- bulk and programmatic environment creation are unaffected. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
When the extension auto-installs a Python via uv, discovery can select uv's version-named launcher shim on PATH (e.g. ~/.local/bin/python3.8.exe) as the base interpreter. Passing that shim to `uv venv --python <shim>` fails for Python <= 3.10 because uv cannot inspect it -- the launched interpreter cannot locate its standard library and aborts with "No module named 'encodings'". The real interpreter (in the uv-managed install folder) works for every version. createWithProgress now resolves the base interpreter via getBaseInterpreterForVenv: when the environment's executable lives outside its own sysPrefix (a launcher/shim), it uses the interpreter inside the prefix (<sysPrefix>/python.exe or bin/python[3]) instead, falling back to the original executable if none exist. Applied to both the `uv venv` and `python -m venv` paths, so it is a no-op for normal interpreters and also prevents a shim-built venv from recording a pyvenv.cfg `home` whose python.exe does not exist (which would make the base-existence check fail on every reuse). Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Stella Huang (StellaHuang95)
marked this pull request as ready for review
September 4, 2026 19:55
Stella Huang (StellaHuang95)
enabled auto-merge (squash)
September 4, 2026 20:22
| * "No compatible Python" message. Calls out an exact two-segment pin like `==3.11` (PEP 440 = | ||
| * exactly 3.11.0, often not installable) so the user understands why nothing matched. | ||
| */ | ||
| function buildNoCompatiblePythonMessage(requiresPython?: string): string { |
Contributor
There was a problem hiding this comment.
Can this maybe use the new PythonVersion class for pargins and extracting major/minor?
Eduardo Villalpando Mello (edvilme)
approved these changes
Sep 4, 2026
Stella Huang (StellaHuang95)
merged commit Sep 4, 2026
731b31c
into
microsoft:main
45 of 46 checks passed
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.
Summary
Two related fixes for the (internally-flagged) PEP 723 inline-script environment feature, found while manually testing the "Set up environment for this script" CodeLens.
1. Surface inline-script setup failures instead of failing silently
Previously, clicking the CodeLens and having setup produce no environment was silent — the reason lived only in the Python Environments output log. The interactive setup command now surfaces an actionable message:
no-compatible-pythoncase, with a note whenrequires-pythonis an exact two-segment pin like==3.11(PEP 440 treats it as exactly3.11.0, which is often not installable);The env manager records the setup outcome (failed reason or benign skip) on the shared
InlineScriptRoutingRegistryas a diagnostic side-channel; the setup command reads it once to choose the message. Only the interactive CodeLens flow shows messages — bulk and programmatic environment creation are unaffected.2. Build inline-script venvs from the real interpreter, not a uv shim
When the extension auto-installs a Python via uv, discovery can select uv's version-named launcher shim on
PATH(e.g.~/.local/bin/python3.8.exe) as the base interpreter. Passing that shim touv venv --python <shim>fails for Python ≤ 3.10 — uv can't inspect it; the launched interpreter can't locate its standard library and aborts withNo module named 'encodings'. (Python 3.11+ tolerates it.) The real interpreter in the uv-managed install folder works for every version.createWithProgressnow resolves the base via a newgetBaseInterpreterForVenv: when the environment's executable lives outside its ownsysPrefix(a launcher/shim), it uses the interpreter inside the prefix (<sysPrefix>/python.exeorbin/python[3]), falling back to the original executable if none exist. Applied to both theuv venvandpython -m venvpaths. It is a no-op for normal interpreters, and it also prevents a shim-built venv from recording apyvenv.cfghomewhosepython.exedoes not exist (which would otherwise make the base-existence check report the base as missing on every reuse).Testing
npm run compile-tests+ unit suite: 2001 passing / 0 failing (3 new tests forgetBaseInterpreterForVenv).uv venv --python <shim>fails for 3.8 whileuv venv --python <real interpreter>succeeds; the failure boundary is exactly Python ≤ 3.10.