uv icon indicating copy to clipboard operation
uv copied to clipboard

Request: Allow --output-file, --annotation-style, etc. multiple times, only use right-most

Open AndydeCleyre opened this issue 1 year ago • 17 comments

requirements.in:

requests
$ uv pip compile requirements.in -o reqs1.txt -o reqs2.txt
error: the argument '--output-file <OUTPUT_FILE>' cannot be used multiple times
$ uv --version
uv 0.1.37
$ uname
Linux

I'm requesting that instead, the above command write output to (only) reqs2.txt, the latest instance of -o/--output-file on the command line. This is useful when using shell aliases or functions to wrap uv, when you specify a "default" output file in the alias or function, while allowing any invocation to easily override that default by specifying the option again, on the command line.

That's how pip-tools behaves, and I make use of that behavior.

AndydeCleyre avatar Apr 24 '24 16:04 AndydeCleyre

I think I'd find this behavior really confusing. What if we provided a UV_COMPILE_OUTPUT_FILE environment variable instead that you could override with the command line?

zanieb avatar Apr 24 '24 17:04 zanieb

This would also be resolved by #3049 / #1511 I presume?

zanieb avatar Apr 24 '24 17:04 zanieb

A file-based configuration or global configuration would not work for my case, which is functions that have their own defaults but are separate from any other ways the user wishes to use pip or uv.

With UV_COMPILE_OUTPUT_FILE, let me think: if uv is the backend being used I could add my own parsing of all the options, find and remove all output flags, use the last one to set UV_COMPILE_OUTPUT_FILE, and run my commands. It might be workable for my main case, but adds a lot of complication for the uv code path. Certainly not suitable for aliases.

FWIW, this is a very common convention (later options "win"), and is used not just by pip-tools but also pip itself. For example, the following command only uses the cache2 folder:

$ pip install --cache-dir="$PWD/cache1" requests --cache-dir="$PWD/cache2"

AndydeCleyre avatar Apr 24 '24 17:04 AndydeCleyre

Certainly not suitable for aliases.

I think you'd just write a simple bash function instead of an alias that sets a default value for the variable before calling into uv?

FWIW, this is a very common convention (later options "win"), and is used not just by pip-tools but also pip itself. For example, the following command only uses the cache2 folder:

I think with something like --cache-dir it's much clearer that a single cache directory can be used whereas with --output-file I would be uncertain if multiple output files will be written.

zanieb avatar Apr 24 '24 18:04 zanieb

FWIW here's maybe a more analogous option from pip:

$ pip install --dry-run --quiet --report=out1.json requests --report=out2.json

As expected, only out2.json is written.

AndydeCleyre avatar Apr 24 '24 18:04 AndydeCleyre

Similarly, both busybox wget and GNU wget use the latest-provided options for output file.

AndydeCleyre avatar Apr 24 '24 18:04 AndydeCleyre

I'll note that I am having similar troubles with e.g. --annotation-style, which I expected to work like it does in pip-tools (latest wins). I won't open a separate issue for that at this time, as it gets to the same larger question.

AndydeCleyre avatar Apr 24 '24 18:04 AndydeCleyre

I suspect part of this comes from argparse's design. Many python libraries use argparse/similar library. argparse's default behavior is last one wins with no awareness of meaning flag.

edit: Personally I like current duplicates are hard error over last one wins. My guess is it's commonness in python ecosystem is less that clis made choice individually, but argument handling libraries default choices made it common.

hmc-cs-mdrissi avatar Apr 25 '24 00:04 hmc-cs-mdrissi

Yup, argparse does it. So does Click. So does go-flags. And bazel. Looks like rustc will be doing it (if I'm interpreting that correctly).

AndydeCleyre avatar Apr 25 '24 02:04 AndydeCleyre

Is this the same? https://github.com/clap-rs/clap/issues/4261

charliermarsh avatar Apr 25 '24 02:04 charliermarsh

Yeah, looks like exactly that.

AndydeCleyre avatar Apr 25 '24 03:04 AndydeCleyre

I think you can set this globally with something like https://docs.rs/clap/latest/clap/struct.Command.html#method.args_override_self.

charliermarsh avatar Apr 25 '24 03:04 charliermarsh