git@vger.kernel.org mailing list mirror (one of many)
 help / color / mirror / code / Atom feed
From: Junio C Hamano <gitster@pobox.com>
To: git@vger.kernel.org
Cc: "Sergey Organov" <sorganov@gmail.com>,
	"Jean-Noël AVILA" <avila.jn@gmail.com>,
	"Kristoffer Haugsbakk" <code@khaugsbakk.name>
Subject: Re: [PATCH v2] clean: improve -n and -f implementation and documentation
Date: Sun,  3 Mar 2024 14:05:59 -0800	[thread overview]
Message-ID: <20240303220600.2491792-1-gitster@pobox.com> (raw)
In-Reply-To: <7le6ziqzb.fsf_-_@osv.gnss.ru>

Sergey Organov <sorganov@gmail.com> writes:

> Changes since v1:
>
>  * Fixed style of the if() statement
>
>  * Merged two error messages into one
>
>  * clean.requireForce description changed accordingly

Excellent.

> diff --git a/builtin/clean.c b/builtin/clean.c
> index d90766cad3a0..41502dcb0dde 100644
> --- a/builtin/clean.c
> +++ b/builtin/clean.c
> @@ -25,7 +25,7 @@
>  #include "help.h"
>  #include "prompt.h"
>  
> -static int force = -1; /* unset */
> +static int require_force = -1; /* unset */
>  static int interactive;
>  static struct string_list del_list = STRING_LIST_INIT_DUP;
>  static unsigned int colopts;
> @@ -128,7 +128,7 @@ static int git_clean_config(const char *var, const char *value,
>  	}
>  
>  	if (!strcmp(var, "clean.requireforce")) {
> -		force = !git_config_bool(var, value);
> +		require_force = git_config_bool(var, value);
>  		return 0;
>  	}
>  
> @@ -920,7 +920,7 @@ int cmd_clean(int argc, const char **argv, const char *prefix)
>  {
>  	int i, res;
>  	int dry_run = 0, remove_directories = 0, quiet = 0, ignored = 0;
> -	int ignored_only = 0, config_set = 0, errors = 0, gone = 1;
> +	int ignored_only = 0, force = 0, errors = 0, gone = 1;
>  	int rm_flags = REMOVE_DIR_KEEP_NESTED_GIT;
>  	struct strbuf abs_path = STRBUF_INIT;
>  	struct dir_struct dir = DIR_INIT;
> @@ -946,22 +946,17 @@ int cmd_clean(int argc, const char **argv, const char *prefix)
>  	};
>  
>  	git_config(git_clean_config, NULL);
> -	if (force < 0)
> -		force = 0;
> -	else
> -		config_set = 1;

The above changes are a significant improvement.  Instead of a
single "force" variable whose meaning is fuzzy, we now have
"require_force" to track the config setting, and "force" to indicate
the "--force" option.  THis makes the code's intent much clearer.

>  	argc = parse_options(argc, argv, prefix, options, builtin_clean_usage,
>  			     0);
>  
> -	if (!interactive && !dry_run && !force) {
> -		if (config_set)
> -			die(_("clean.requireForce set to true and neither -i, -n, nor -f given; "
> -				  "refusing to clean"));
> -		else
> -			die(_("clean.requireForce defaults to true and neither -i, -n, nor -f given;"

And thanks to that, the above trick with an extra variable "config_set",
which smells highly a round-about way, can be simplified.

> +	/* Dry run won't remove anything, so requiring force makes no sense */
> +	if (dry_run)
> +		require_force = 0;
> +	if (require_force != 0 && !force && !interactive)

However, the above logic could be improved.  The behaviour we have,
for a user who does *not* explicitly disable config.requireForce,
is, that when clean.requireForce is not set to 0, we would fail
unless one of these is in effect: -f, -n, -i.  Even though using
either -n or -i makes it unnecessary to use -f *exactly* the same
way, the above treats dry_run and interactive separately with two if
statements, which is suboptimal as a "code/logic clean-up".

The reason for the behaviour can be explained this way:

 * "git clean" (with neither -i nor -n.  The user wants the default
   mode that has no built-in protection will be stopped without -f.

 * "git clean -n".  The user wants the dry-run mode that has its own
   protection, i.e. being always no-op to the files, so there is no
   need to fail here for the lack of "-f".

 * "git clean --interactive".  The user wants the interactive mode
   that has its own protection, i.e. giving the end-user a chance to
   say "oh, I didn't mean to remove these files, 'q'uit from this
   mistake", so there is no need to fail here for the lack of "-f".

> +		die(_("clean.requireForce is true and neither -f nor -i given:"
>  				  " refusing to clean"));

The message is certainly cleaner compared to the previous round, but
this also can be improved.  Stepping back a bit and thinking who are
the target audience of this message.  The only users who see this
message are running "git clean" in its default (unprotected) mode,
and they wanted to "clean" for real.  If they wanted to do dry-run,
they would have said "-n" themselves, and that is why we can safely
omit mention of "-n" we had in the original message.

These users did not want to run the interractive clean, either---if
they wanted to go interractive, they would have said "-i"
themselves.  So we do not need to mention "-i" either for exactly
the same logic.

Based on the above observation,

I'll send a follow-up patch to clean up the code around here (both
implementation and documentation), taking '-i' into account as well.


       reply	other threads:[~2024-03-03 22:06 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <7le6ziqzb.fsf_-_@osv.gnss.ru>
2024-03-03 22:05 ` Junio C Hamano [this message]
2024-03-03 22:06   ` [PATCH 1/1] clean: further clean-up of implementation around "--force" Junio C Hamano
2024-03-03 22:18     ` Junio C Hamano
2024-03-04 18:46     ` Sergey Organov
2024-03-04 18:39   ` [PATCH v2] clean: improve -n and -f implementation and documentation Sergey Organov
2024-03-04 18:41     ` Junio C Hamano
2024-03-04 18:48       ` Sergey Organov
2024-03-04 19:03     ` Junio C Hamano
2024-03-04 20:19       ` Sergey Organov
2024-01-09 20:20 what should "git clean -n -f [-d] [-x] <pattern>" do? Junio C Hamano
2024-02-29 19:07 ` [PATCH] clean: improve -n and -f implementation and documentation Sergey Organov
2024-03-03  9:50   ` [PATCH v2] " Sergey Organov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: http://vger.kernel.org/majordomo-info.html

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20240303220600.2491792-1-gitster@pobox.com \
    --to=gitster@pobox.com \
    --cc=avila.jn@gmail.com \
    --cc=code@khaugsbakk.name \
    --cc=git@vger.kernel.org \
    --cc=sorganov@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://80x24.org/mirrors/git.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).