Live data from Hacker News

Uv's killer feature is making ad-hoc environments easy

valatka.dev

221–230 of 428 posts

Re: Uv's killer feature is making ad-hoc environments easy

#221
post #163
post #157

Earlier quoted context omitted.

Yes, generally people already use an additional tool for managing their Python executables, like their operating system's package manager: $> sudo apt-get install python3.10 python3.11 python3.12 And then it's simple to create and use version-specific virtual environments: $> python3.11 -m venv .venv3.11 $> source .venv3.11/bin/activate $> pip install -r requirements.txt You are incorrect about needing to use an addi…

> sudo apt-get install python3.10 python3.11 python3.12 This assumes the Python version you need is available from your package manager's repo. This won't work if you want a Python version either newer or older than what is available. > You are incorrect about needing to use an additional tool to install a "global" tool like `ruff`; `pip` does this by default when you're not using a virtual environment. True, but it'…

> pip doesn't resolve dependencies of dependencies.

This is simply incorrect. In fact the reason it gets stuck on resolution sometimes is exactly because it resolved transitive dependencies and found that they were mutually incompatible.

Here's an example which will also help illustrate the rest of my reply. I make a venv for Python 3.8, and set up a new project with a deliberately poorly-thought-out pyproject.toml:

  [project]
  name="example"
  version="0.1.0"
  dependencies=["pandas==2.0.3", "numpy==1.17.3"]
I've specified the oldest version of Numpy that has a manylinux wheel for Python 3.8 and the newest version of Pandas similarly. These are both acceptable for the venv separately, but mutually incompatible on purpose.

When I try to `pip install -e .` in the venv, Pip happily explains (granted the first line is a bit strange):

  ERROR: Cannot install example and example==0.1.0 because these package versions have conflicting dependencies.

  The conflict is caused by:
      example 0.1.0 depends on numpy==1.17.3
      pandas 2.0.3 depends on numpy>=1.20.3; python_version 
If I change the Numpy pin to 1.20.3, that's the version that gets installed. (`python-dateutil`, `pytz`, `six` and `tzdata` are also installed.) If I remove the Numpy requirement completely and start over, Numpy 1.24.4 is installed instead - the latest version compatible with Pandas' transitive specification of the dependency. Similarly if I unpin Pandas and ask for any version - Pip will try to install the latest version it can, and it turns out that the latest Pandas version that declares compatibility with 3.8, indeed allows for fetching 3.8-compatible dependencies. (Good job not breaking it, Pandas maintainers! Although usually this is trivial, because your dependencies are also actively maintained.)

> pip will only respect version pinning for dependencies you explicitly specify. So for example, say I am using pandas and I pin it to version X. If a dependency of pandas (say, numpy) isn't pinned as well, the underlying version of numpy can still change when I reinstall dependencies.

Well, sure; Pip can't respect a version pin that doesn't exist anywhere in your project. If the specific version of Pandas you want says that it's okay with a range of Numpy versions, then of course Pip has freedom to choose one of those versions. If that matters, you explicitly specify it. Other programs like uv can't fix this. They can only choose different resolution strategies, such as "don't update the transitive dependency if the environment already contains a compatible version", versus "try to use the most recent versions of everything that meet the specified compatibility requirements".

> To get around this with pip you would need an additional tool like pip-tools, which allows you to pin all dependencies, explicit and nested, to a lock file for true reproducibility.

No, you just use Pip's options to determine what's already in the environment (`pip list`, `pip freeze` etc.) and pin everything that needs pinning (whether with a Pip requirements file or with `pyproject.toml`). Nothing prevents you from listing your transitive dependencies in e.g. the [project.dependencies] of your pyproject.toml, and if you pin them, Pip will take that constraint into consideration. Lock files are for when you need to care about alternate package sources, checking hashes etc.; or for when you want an explicit representation of your dependency graph in metadata for the sake of other tooling.

> This assumes the Python version you need is available from your package manager's repo. This won't work if you want a Python version either newer or older than what is available.

I have built versions 3.5 through 3.13 inclusive from source and have them installed in /opt and the binaries symlinked in /usr/local/bin. It's not difficult at all.

> True, but it's not best practice to do that because while the tool gets installed globally, it is not necessarily linked to a specific python version, and so it's extremely brittle.

What brittleness are you talking about? There's no reason why the tool needs to run in the same environment as the code it's operating on. You can install it in its own virtual environment, too. Since tools generally are applications, I use Pipx for this (which really just wraps a bit of environment management around Pip). It works great; for example I always have the standard build-frontend `build` (as `pyproject-build`) and the uploader `twine` available. They run from a guaranteed-compatible Python.

And they would if they were installed for the system Python, too. (I just, you know, don't want to do that because the system Python is the system package manager's responsibility.) The separate environment don't matter because the tool's code and the operated-on project's code don't even need to run at the same time, let alone in the same process. In fact, it would make no sense to be running the code while actively trying to build or upload it.

> And it gets even more complex if you need different tools that have different Python version requirements.

No, you just let each tool have the virtual environment it requires. And you can update them in-place in those environments, too.

Re: Uv's killer feature is making ad-hoc environments easy

#223

Earlier quoted context omitted.

What is the deal with uv's ownership policy? I heard it might be VC backed. To my mind, that means killing pip and finding some kind of subscription revenue source which makes me uneasy. The only way to justify VC money is a plot to take over the ecosystem and then profit off of a dominant position. (e.g. the Uber model) I've heard a little bit about UV's technical achievements, which are impressive, but technical pr…

It’s dual MIT and Apache licensed. Worst case, if there’s a rug pull, fork it.

Is that the entire story? If so the VCs are pretty dumb. If they kill pip, that means the people who were maintaining it disperse and forking it won't restore the ecosystem that was there before.

Re: Uv's killer feature is making ad-hoc environments easy

#224
post #171
post #157

Earlier quoted context omitted.

Yes, generally people already use an additional tool for managing their Python executables, like their operating system's package manager: $> sudo apt-get install python3.10 python3.11 python3.12 And then it's simple to create and use version-specific virtual environments: $> python3.11 -m venv .venv3.11 $> source .venv3.11/bin/activate $> pip install -r requirements.txt You are incorrect about needing to use an addi…

(I've just learned about uv, and it looks like I have to pick it up since it performs very well.) I just use pipx. Install guides suggest it, and it is only one character different from pip. With Nix, it is very easy to run multiple versions of same software. The path will always be the same, meaning you can depend on versions. This is nice glue for pipx. My pet peeve with Python and Vim is all these different packag…

Pipx is a tool for users to install finished applications. It isn't intended for installing libraries for further development, and you have to hack around it to make that work. (This does gain you a little bit over using Pip directly.)

I just keep separate compiled-from-source versions of Python in a known, logical place; I can trivially create venvs from those directly and have Pip install into them, and pass `--python` to `pipx install`.

>With Python it is pip, poetry, pip search no longer working, pipx, and now uv (I probably forgot some things).

Of this list, only Poetry and Uv are package managers. Pip is by design, only an installer, and Pipx only adds a bit of environment management to that. A proper package manager also helps you keep track of what you've installed, and either produces some sort of external lock file and/or maintains dependency listings in `pyproject.toml`. But both Poetry and Uv go further beyond that as well, aiming to help with the rest of the development workflow (such as building your package for upload to PyPI).

If you like Pipx, you might be interested in some tips in my recent blog post (https://zahlman.github.io/posts/2025/01/07/python-packaging-...). In particular, if you do need to install libraries, you can expose Pipx's internal copy of Pip for arbitrary use instead of just for updating the venvs that Pipx created.

Re: Uv's killer feature is making ad-hoc environments easy

#225
post #197
post #57

Earlier quoted context omitted.

Because node.js isn't a dependency of the Operating system. Also we don't have a left pad scale dependency ecosystem that makes version conflicts such a pressing issue.

Oh, tell us OS can’t venv itself a separate python root and keep itself away from what user invents to manage deps. This is non-explanation appealing to authority while it’s clearly just a mess lacking any thought. It just works like this. we don't have a left pad scale dependency ecosystem that makes version conflicts such a pressing issue TensorFlow.

We have virtual envs and package isolation, it's usually bloated, and third party and doesn't make for a good robust OS base, it's more an app layer. See flatpak, snapcraft.

"Compares left pad with ml library backing the hottest AI companies of the cycle"

Re: Uv's killer feature is making ad-hoc environments easy

#226

Earlier quoted context omitted.

The PEP page is really good at explaining the status of the proposal, a summary of the discussion to date, and then links to the actual detailed discussion (in Discourse) about it: https://peps.python.org/pep-0723/

I see this was accepted (I think?); is the implementation available in a released python version? I don't see an "as of" version on the pep page, nor do lite google searches reveal any official python docs of the feature.

This is a specification for Python packaging, which is tooling separate from Python releases (for better or worse, IMHO worse but the BDFL disagrees). There's a box below the Table of Contents of the PEP that points here:

https://packaging.python.org/en/latest/specifications/inline...

Re: Uv's killer feature is making ad-hoc environments easy

#227

Earlier quoted context omitted.

Couple of things. - pip doesn't handle your Python executable, just your Python dependencies. So if you want/need to swap between Python versions (3.11 to 3.12 for example), it doesn't give you anything. Generally people use an additional tool such as pyenv to manage this. Tools like uv and Poetry do this as well as handling dependencies - pip doesn't resolve dependencies of dependencies. pip will only respect versio…

Oh wow, it actually can handle the Python executable? I didn't know that, that's great! Although it's in the article as well, it didn't click until you said it, thanks!

I still don't understand why people want separate tooling to "handle the Python executable". All you need to do is have one base installation of each version you want, and then make your venv by running the standard library venv for that Python (e.g. `python3.x -m venv .venv`).

Re: Uv's killer feature is making ad-hoc environments easy

#228

Earlier quoted context omitted.

Oh wow, it actually can handle the Python executable? I didn't know that, that's great! Although it's in the article as well, it didn't click until you said it, thanks!

I still don't understand why people want separate tooling to "handle the Python executable". All you need to do is have one base installation of each version you want, and then make your venv by running the standard library venv for that Python (e.g. `python3.x -m venv .venv`).

> All you need to do is have one base installation of each version you want

Because of this ^

Re: Uv's killer feature is making ad-hoc environments easy

#229

Earlier quoted context omitted.

My experience was that docker was a tool data scientists would use to speedrun the process of finding broken Pythons. For instance we'd inexplicably find a Python had Hungarian as the default charset, etc. The formula was - Docker - Discipline = Chaos Docker - Discipline = Chaos Docker + Discipline = Order but - Docker + Discipline = Order If you can write a Dockerfile to install something you can write a bash script…

> For instance we'd inexplicably find a Python had Hungarian as the default charset, etc. Sounds quite explicable: Docker image created by Hungarian devs perhaps?

My understanding is that UTF-8 is the world's charset and that reasonable Hungarians would use that (e.g. I sure don't use us-ascii or iso-latin-1 if I can at all help it. I mean my "better half" reads 中文 so I don't have to and having it all in UTF-8 makes it easy) The other mystery is how the data sci's found it.

Re: Uv's killer feature is making ad-hoc environments easy

#230

Earlier quoted context omitted.

Oh wow, it actually can handle the Python executable? I didn't know that, that's great! Although it's in the article as well, it didn't click until you said it, thanks!

I still don't understand why people want separate tooling to "handle the Python executable". All you need to do is have one base installation of each version you want, and then make your venv by running the standard library venv for that Python (e.g. `python3.x -m venv .venv`).

I'm glad to let uv handle that for me. It does a pretty good job at it!
Post reply on HN