Comment by thanhhaimai

Comment by thanhhaimai 2 days ago

78 replies

I'd rather `ruff` being merged with `ty` instead. `uv` for me is about package / project manager. It's not about code style. The only time `uv` should edit a code file is to update its dependencies (PEP 723).

On the other hand, both `ruff` and `ty` are about code style. They both edit the code, either to format or fix typing / lint issues. They are good candidates to be merged.

charliermarsh 2 days ago

To clarify, `ruff` and `uv` aren't being merged. They remain separate tools. This is more about providing a simpler experience for users that don't want to think about their formatter as a separate tool.

The analogy would be to Cargo: `cargo fmt` just runs `rustfmt`, but you can also run `rustfmt` separately if you want.

  • WD-42 2 days ago

    Thank you for writing software for all of us Python day-jobbers who wish we were writing Rust instead.

    • weakfish 2 days ago

      Never seen someone put my feeling so succinctly

    • echelon 2 days ago

      You can advocate for using Rust at work.

      If you're writing microservices, the Rust ecosystem sells itself at this point.

      • foxygen a day ago

        What Rust has over other languages that makes it better for writing microservices?

  • drdaeman 2 days ago

    Isn’t there `uv tool run ruff` already for this? Or `uv run ruff` if it’s a proper dependency? I’m not sure what’s the point of a special shortcut command, unless there are plans to make it flexible so it’ll be an abstraction over formatters (unifying ruff, black, etc).

    • charliermarsh 2 days ago

      Yeah, you can definitely use `uvx ruff` (an alias for `uv tool run ruff`) to invoke Ruff. That's what I've done in my own projects historically.

      The goal here is to see if users like a more streamlined experience with an opinionated default, like you have in Rust or Go: install uv, use `uv init` to create a project, use `uv run` to run your code, `uv format` to format it, etc. Maybe they won't like it! TBD.

      (Ruff is installed when you invoke `uv format`, rather than bundled with the uv binary, so if you never use `uv format`, there aren't any material downsides to the experiment.)

      • divbzero 2 days ago

        > (Ruff is installed when you invoke `uv format`, rather than bundled with the uv binary, so if you never use `uv format`, there aren't any material downsides to the experiment.)

        That’s thoughtful design and could be worth mentioning in the blog post.

      • RS-232 2 days ago

        Would you ever consider bundling ruff binaries with uv releases similar to uvx and uvw? It would benefit offline users and keep compatible uv/ruff versions in sync.

        Perhaps even better… cargo-like commands such as uv check, uv doc, and uv test could subsume ruff, ty, and other tools that we haven’t seen yet ;)

        A pyup command that installs python-build-standalone, uv, python docs, etc. would be totally clutch, as would standalone installers [0] that bundle it all together.

        [0] https://forge.rust-lang.org/infra/other-installation-methods...

    • chippiewill 2 days ago

      It's part of the mission for uv to become "cargo for python". A one stop swiss-army knife for everything you need to manage a Python project. I think it'll get a `uv test` command at some point too.

      The whole point is you just install `uv` and stop thinking about the pantheon of tools.

      • robertlagrant 2 days ago

        It'll be interesting to see how the test is done. At the tox level, or the pytest level? (Or another level?) I can see all being useful and ergonomic, but tox's multi-environment setup might fit into it really well.

  • godelski 2 days ago

    Is `uv format` supposed to be an alias for `ruff check`?

    Stupidly I ran `uv format` without `--check` (no harm done and I can `git diff` it) so I didn't see the changes it made but `ruff check` does still show things that can be fixed with `ruff check --fix`. If I'm guessing correctly the difference is coming down to the fact that I have (in my submodule where all changes were made) a pyproject.toml file with ruff rules (there's also a .flake8 file. Repo is being converted). Either way, I find this a bit confusing userside. Not sure what to expect.

    I think one thing I would like is that by default `uv format` spits out what files were changed like `uv format --check` does (s/Would reformat/Reformatted/g). Fine for the actual changes not to be displayed but I think this could help with error reduction. Running it again I can see it knows 68 files were changed. Where is that information being stored? It's pretty hard to grep out a number like that (`grep -R \<68\>`) and there's a lot of candidates (honestly there's nothing that looks like a good candidate).

    Also, there's a `--quiet` flag, but the output is already pretty quiet. As far as I can tell the only difference is that quiet suppresses the warning (does `--quiet` also suppress errors?)

      uv format
      warning: `uv format` is experimental and may change without warning. Pass `--preview-features format` to disable this warning.
      36 files reformatted, 31 files left unchanged
    
      uv format --quiet
      36 files reformatted, 31 files left unchanged
    
    I like the result for `--quiet` but I have a strong preference that `uv format` match the verbosity of `uv format --check`. I can always throw information away but not recover. I have a strong bias that it is better to fail by displaying too much information than fail by displaying too little. The latter failure mode is more harmful as the former is much more easily addressed by existing tools. If you're taking votes, that's mine.

    Anyways, looking forward to seeing how this matures. Loved everything so far!

    • akx 2 days ago

      > Is `uv format` supposed to be an alias for `ruff check`?

      I'd imagine not, since `ruff format` and `ruff check` are separate things too.

      • godelski a day ago

        That makes some more sense. I think I just misunderstood what Charlie was saying above.

        But I'll also add another suggestion/ask. I think this could be improved

          $ ruff format --help
          Run the Ruff formatter on the given files or directories
          $ uv format --help
          Format Python code in the project
        
        I think just a little more can go a long way. When --help is the docs instead of man I think there needs to be a bit more description. Just something like this tells users a lot more

          $ ruff format --help
          Formats the specified files. Acts as a drop-in replacement for black. 
          $ uv format --help
          Experimental uv formatting. Alias to `ruff format`
        
        I think man/help pages are underappreciated. I know I'm not the only one that discovers new capabilities by reading them. Or even the double tab because I can't remember the flag name but see something I didn't notice before. Or maybe I did notice before but since the tool was new I focused on main features first. Having the ability to read enough information to figure out what these things do then and there really speeds up usage. When the help lines don't say much I often never explore them (unless there's some gut feeling). I know the browser exists, but when I'm using the tool I'm not in the browser.
  • slightwinder 2 days ago

    > To clarify, `ruff` and `uv` aren't being merged.

    ruff at least seems to be compiled into uv, as the format worked here without a local ruff. This is significant more than just an interface. Whether they are managed and developed as separate tools doesn't matter.

    > This is more about providing a simpler experience for users that don't want to think about their formatter as a separate tool.

    Then build a separate interface, some script/binary acting as a unified interface, maybe with its separate distribution of all tools. Pushing it into uv is just adding a burden to those who don't want this.

    uv and ruff are poor names anyway, this could be used to at least introduce a good name for this everything-python-tool they seem to aim for.

    • woodruffw 2 days ago

      ruff is not compiled into uv; it's bootstrapped from an independent build, much like how `cargo fmt` is bootstrapped from a separate toolchain component (rustfmt). You can see how that works in the PR[1]. Importantly, that means that you don't experience any build-, install-, or run-time burden if you don't use this subcommand.

      [1]: https://github.com/astral-sh/uv/pull/15017

  • rbits 2 days ago

    Does it have the capability to use a different formatter than ruff?

    • ZiiS 2 days ago

      This is about providing an opinionated default. uv will still support installing and runing any formater as before.

  • jgauth 2 days ago

    This is cool. Is there a way to call ruff’s linter? Like `uv lint`, which would call `ruff check`.

    To your analogy, it’d be like `cargo clippy`

    • godelski 2 days ago

      You can always use `uvx ruff check` or `uv tool run ruff check`. Though honestly I find just running `ruff check` much easier.

  • [removed] 2 days ago
    [deleted]
WD-42 2 days ago

They are mimicking Rust's cargo, which has `cargo fmt`

  • Biganon 2 days ago

    > They are mimicking Rust's cargo

    Cargo cargo cult?

    • xdennis a day ago

      It's not a cargo cult if it actually works.

  • petcat 2 days ago

    Doesn't cargo just have a subcommand plugin system? Or is fmt actually hard-coded into the cargo code?

    I prefer the plugin system. I don't like god programs like what the npm monstrosity became.

    • woodruffw 2 days ago

      cargo has an external subcommand system, but it also has "blessed" (my word choice) external subcommands that are typically bootstrapped via Rust toolchain components. This makes them pretty analogous to what uv does here with `uv format`, in my opinion.

impulser_ 2 days ago

I think the goal is to make uv a complete package manager for Python while still giving you the option to use the parts separately.

uv is like cargo for python.

If you only need a fast type checker you can just use ty, if you just need a fast formatter and linter you can just use ruff.

Combining ruff and ty doesn't make sense if you think about like this.

  • RossBencina 2 days ago

    Including a formatter in a package manager doesn't make sense to me. Seems like obvious feature creep.

    My understanding was that uv is for installing dependencies (e.g. like pip) with the added benefit of also installing/managing python interpreters (which can be reasonably thought of as a dependency). This makes sense. Adding more stuff doesn't make sense.

    • masklinn 2 days ago

      GP should have written project manager not package.

      Think npm / go / cargo, not apt/yum/pip.

      • Kwpolska 2 days ago

        Doesn't make it less feature creep.

    • tuetuopay 2 days ago

      Doing a lot of Rust, there is one huge benefit of having cargo handle rustfmt: it knows the fileset you're talking about. It will not blindly format all rust files in the cwd, rather the "current" crate (current having the same definition as cargo!).

      Translating this to uv, this will streamline having multiple python packages in the same directory/git repo, and leave e.g. vendored dependencies alone.

      Also, since their goal really is "making cargo for python", it will likely support package-scoped ruff config files, instead of begin file- or directory-based.

  • baggiponte 2 days ago

    i think it's good to let them experiment! cargo (and go?) offers this already, so why not.

munro 2 days ago

But what if `ty` was also eventually merged into `uv` as well? 8-)

That's probably the vision, given all from astral.sh, but `ty` isn't ready yet.

alfalfasprout 2 days ago

Oh please no...

The reality is, ecosystems evolve. First, we had mypy. Then more type checkers came out: pyre, pyright, etc. Then basedpyright. The era of rust arrived and now we have `ty` and `pyrefly` being worked on heavily.

On the linter side we saw flake8, black, and then ruff.

Decoupling makes adapting to evolution much easier. As long as both continue to offer LSP integrations it allows engineers to pick and chose what's best.

  • d0mine 2 days ago

    The whole premise of uv that you don't need to know that you can install specific python version using eg pyenv (`uv python install` or `uv run` may do it implicitly), you don't need to know about `python -m venv`/virtualenv (`uv venv`), or how to create lock files pip-tools / pipenv / poetry / etc(`uv lock`), or pipx (`uv tool install`) or `pip install`/ `pipenv install`/`poetry add` / many others (`uv add`), or how to build artifacts setuptools / hatchling / poetry way / etc (`uv build`). Other commands such as `uv sync` didn't break new ground too.

    `uv format` is similar (you don't need to know about `ruff format` / black / yapf ).

    • Kwpolska 2 days ago

      All actions listed in your first paragraph, except for installing specific Python versions, are actions related to the area of packaging. Doing it in one tool is completely sensible. I'm not a fan of uv managing Pythons, but I guess that ship has sailed.

      But formatting code is a completely new area that does not fit uv.

darkamaul 2 days ago

And I would think the next logical step here is to have a `uv lint` option here that runs ˋty` under the hood ?

I would love to see a world where there is a single or a set of standard commands that would prepare your python project (format, lint, test, publish). Maybe that’s the vision here?

zahlman 2 days ago

This is the direction I expected things to go, and not something I'm especially fond of. I'll stick with UNIX-philosophy tools, thanks.

  • zem 2 days ago

    this is very much in line with the unix philosophy - it delegates formatting to ruff and simply provides a unified front end that calls out to the right specialized tool. think of it as a makefile.

    • zvr 2 days ago

      A better example might be: in good ol' days when we were formatting with troff(1), passing arguments to the command line invoked other programs like eqn(1) and tbl(1).

    • zahlman 2 days ago

      I don't think this is an apt (pun intended?) comparison at all.

      • d0mine 2 days ago

        One can find repos using `make format` / `make lint`/ `make typecheck` / or similar

        I remember David Beazley mentioning that code with Makefiles were relatively easier to analyze based on ~Terabyte of C++ code and no internet connection (pycon 2014) https://youtube.com/watch?v=RZ4Sn-Y7AP8

    • zelphirkalt 2 days ago

      If I want to call ruff, I can do so myself. Why should I want to call it through uv?

      • woodruffw 2 days ago

        If you want to call ruff directly, this doesn't change anything. It's a purely optional feature.

        However, to answer the question generally: people want this for the same reason that most people call `cargo fmt` instead of running rustfmt[1] directly: it's a better developer experience, particularly if you don't already think of code formatting as an XY-type problem ("I want to format my code, and now I have to discover a formatter" versus "I want to format my code, and my tool already has that").

        [1]: https://github.com/rust-lang/rustfmt

      • wiseowise a day ago

        Some of us prefer well packaged tool that does everything instead of stitching together bazillions of dependencies.

        • zelphirkalt a day ago

          Or maybe some prefer random versions of dependencies being downloaded and running over our code?

  • gchamonlive 2 days ago

    There is wisdom in knowing when -- and how -- to break standards. Don't know if this is the case, but I think it is. If introducing fmt powers to UV meant it had to consider tradeoffs elsewhere where it might hurt its quality somehow then maybe, but in this case UV is more like an umbrella, unifying the interface for pip, venv, builds... And now fmt. All keeping each separate domain isolated without details leaking to one another.

    • zahlman 2 days ago

      What do I gain from adding 'uv' to the start of each of these commands, as opposed to having them all just be separate commands?

      • asa400 2 days ago

        Abstraction. Not having to know all the innards (or even names) of each until you want to. It's all there if you want to, but stuff like uv (or cargo, or go's toolset) greatly simplifies 3 scenarios in particular: starting a new project, joining an existing project, and learning Python for the first time.

        All 3 scenarios benefit from removing the choice of build tool, package manager, venv manager, formatter, linter, etc., and saying, "here, use this and get on with your life".

      • gchamonlive 2 days ago

        I also don't know what I'd gain, but it doesn't mean there isn't practical use for someone else.

        But most importantly, apart from breaking away from "UNIX-philosophy tools", what do you lose in practical terms?

      • bowsamic 2 days ago

        Well for one thing separate commands that are as good as what uv does don’t exist

  • Kinrany 2 days ago

    The spirit of the unix philosophy is not implementing MxN use cases separately. Running the same program as a separate binary or as a subcommand has nothing to do with it

  • cedws 2 days ago

    I mean, Go was designed by one of the authors of UNIX, and that has very much batteries-included tooling.

    • lenkite 2 days ago

      So UNIXy that he didn't even like long options (--option) in the standard flag library.

      • ksherlock 2 days ago

        Long options are more of a GNU thing and GNU's Not Unix.