git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: what should "git clean -n -f [-d] [-x] <pattern>" do?

From
Sergey Organov <sorganov@gmail.com>
Date
Jan 25, 2024, 17:11 UTC
Message-ID
<87il3h72ym.fsf@osv.gnss.ru>
In-Reply-To
<xmqqa5ouhckj.fsf@gitster.g>
Junio C Hamano <gitster@pobox.com> writes:
Show 37 quoted lines
> Sergey Organov <sorganov@gmail.com> writes:
>
>> Whereas obsoleting second -f in favor of new --nested-repo might be a
>> good idea indeed, I believe it's still a mistake for "dry run" to
>> somehow interfere with -f, sorry.
>
> No need to be sorry ;-)
>
> I actually think the true culprit of making this an odd-man-out is
> that the use of "-f" in "git clean", especially with its use of the
> configuration variable clean.requireForce that defaults to true, is
> utterly non-standard.
>
> The usual pattern of defining what "-f" does is that the "git foo"
> command without any options does its common thing but refuses to
> perform undesirable operations (e.g. "git add ."  adds everything
> but refrains from adding ignored paths). And "git foo -f" is a way
> to also perform what it commonly skips.
>
> In contrast, with clean.requireForce that defaults to true, "git
> clean" does not do anything useful by default.  Without such a
> safety, "git clean" would be a way to clean expendable paths, and
> "git clean -f" might be to also clean precious paths.  But it does
> not work that way.  It always requires "-f" to do anything.  Worse
> yet, it is not even "by default it acts as if -n is given and -f is
> a way to countermand that implicit -n".  It is "you must give me
> either -f (i.e. please do work) or -n (i.e. please show what you
> would do) before I do anything".
>
>   $ git clean
>   fatal: clean.requireForce defaults to true and neither -i, -n, nor -f given; refusing to clean
>
> Given that, it is hard to argue that it would be a natural end-user
> expectation that the command does something useful (i.e. show what
> would be done) when it is given "-f" and "-n" at the same time.
> What makes this a rather nonsense UI is the fact that "-f" does not
> work the way we would expect for this command.

I think we all agree that current UI is a kind of nonsense, but have different views of the optimal target interface. My points are as following:

1. The fact that bare "git clean" only produces error by default is
probably a good thing, as removal of untracked files is unrecoverable
operation in Git domain, so requiring -f by default is probably a good
thing as well, provided the *only* operation that "git clean" performs
is dangerous enough.
2. The "-n" behavior is pure nonsense.

So, how do we fix (2)? Let's try mental experiment. Suppose there is no "-n" option for "git clean" and we are going to implement it. We start from:

  $ git clean
  fatal: clean.requireForce defaults to true and neither -i nor -f given; refusing to clean
  $ git clean -f
  removing "a"
  removing "b"
  $

Please notice that there is no "-n" in the error message as there is no such option yet in our experiment.

Now we are going to introduce "dry run" option "-n". Most simple and obvious way to do it is to set internal flag "dry_run" and then at every invocation of "remove(file_name)" put an if(dry_run) that will just print(file_name) instead or removing it. Let's suppose we did just that. We get this behavior:

  $ git clean -n
  fatal: clean.requireForce defaults to true and neither -i nor -f given; refusing to clean
  $ git clean -f -n
  would remove "a"
  would remove "b"
  $ git clean -f -f -n
  would remove "a"
  would remove "b"
  would remove "sub/a"
  $

I see this as logical, clean, and straightforward behavior, meeting user expectations for "dry run" option, so I suggest to do just that.

Thanks, -- Sergey Organov.

Previous: Junio C HamanoNext: Junio C Hamano
Message 8 of 38 in “what should "git clean -n -f [-d] [-x] <pattern>" do?”
  1. Junio C HamanoJan 9, 2024
  2. Sergey OrganovJan 9, 2024
  3. Elijah NewrenJan 19, 2024
  4. Sergey OrganovJan 23, 2024
  5. Junio C HamanoJan 23, 2024
  6. Sergey OrganovJan 24, 2024
  7. Junio C HamanoJan 24, 2024
  8. Sergey OrganovJan 25, 2024
  9. Junio C HamanoJan 25, 2024
  10. Sergey OrganovJan 25, 2024
  11. Sergey OrganovJan 25, 2024
  12. Junio C HamanoJan 26, 2024
  13. Sergey OrganovJan 26, 2024
  14. Junio C HamanoJan 27, 2024
  15. Sergey OrganovJan 27, 2024
  16. Kristoffer HaugsbakkJan 29, 2024
  17. Sergey OrganovJan 31, 2024
  18. Sergey OrganovJan 29, 2024
  19. Jeff KingJan 29, 2024
  20. Sergey OrganovJan 29, 2024
  21. Jeff KingJan 30, 2024
  22. Junio C HamanoJan 30, 2024
  23. clean: improve -n and -f implementation and documentationSergey Organov, Feb 29, 2024
  24. Jean-Noël AvilaMar 1, 2024
  25. Sergey OrganovMar 1, 2024
  26. Kristoffer HaugsbakkMar 1, 2024
  27. Junio C HamanoMar 1, 2024
  28. Jean-Noël AVILAMar 2, 2024
  29. Sergey OrganovMar 2, 2024
  30. Junio C HamanoMar 2, 2024
  31. Sergey OrganovMar 2, 2024
  32. Sergey OrganovMar 3, 2024
  33. Junio C HamanoMar 1, 2024
  34. Junio C HamanoMar 1, 2024
  35. Sergey OrganovMar 1, 2024
  36. Junio C HamanoMar 2, 2024
  37. Sergey OrganovMar 2, 2024
  38. clean: improve -n and -f implementation and documentationSergey Organov, Mar 3, 2024

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.