threads / discuss / 27492

git show and the --quiet option

Subject: git show and the --quiet option

## tl;dr

10 messages between May 28, 2011 and Jun 5, 2011.

replies: 9people: 5as markdown or json

Gustaf Hendeby· May 28, 2011, 16:53 UTC · lore
Hello everyone,

I was playing around with "git show" lately and realized it has changed its behavior regarding the --quiet option, which no longer suppresses the diff output as it used to. The behavior change happened in 1c40c36b ("log: convert to parse-options"). Was this intentional?

The commit message talks about the --quiet handling being improved and the "git show" help doesn't mention a --quiet option. Is the simple answer that the previous behavior was incorrect?

/Gustaf
Carlos Martín Nieto· May 28, 2011, 17:26 UTC · re: Gustaf Hendeby · lore

Re: git show and the --quiet option

On Sat, May 28, 2011 at 06:53:28PM +0200, Gustaf Hendeby wrote:
Show 6 quoted lines
> Hello everyone,
> 
> I was playing around with "git show" lately and realized it has changed
> its behavior regarding the --quiet option, which no longer suppresses
> the diff output as it used to.  The behavior change happened in
> 1c40c36b ("log: convert to parse-options").  Was this intentional?
Very much so.
> 
> The commit message talks about the --quiet handling being improved and
> the "git show" help doesn't mention a --quiet option.  Is the simple
> answer that the previous behavior was incorrect?
Yes.
 The long answer is that the log family (and git-format-patch, which
is where this started) never actually accepted --quiet, so it would
get passed down to the diff machinery. This (for complicated reasons
I'm not sure I comletely understand, but that have to do with the
internal handling of 'quiet' as 'quick') caused every second commit
not to show.
 As you noticed, the man page never mentions a --quiet option
(because, honestly, it doesn't make any sense), so any use of that
flag is wrong. Part of what the patch does is make --quiet a no-op to
guard against the effect of disappearing commits.
 How are you using the --quiet option and why would you even need it?
Cheers,
   cmn
-- 
Carlos Martín Nieto | http://cmartin.tk

"¿Cómo voy a decir bobadas si soy mudo?" -- CACHAI
Gustaf Hendeby· May 28, 2011, 18:03 UTC · re: Carlos Martín Nieto · lore

Re: git show and the --quiet option

Hi Carlos,
thanks for the detailed answer.
On 05/28/2011 07:26 PM, Carlos Martín Nieto wrote:
Show 8 quoted lines
> On Sat, May 28, 2011 at 06:53:28PM +0200, Gustaf Hendeby wrote:
>> Hello everyone,
>>
>> I was playing around with "git show" lately and realized it has changed
>> its behavior regarding the --quiet option, which no longer suppresses
>> the diff output as it used to.  The behavior change happened in
>> 1c40c36b ("log: convert to parse-options").  Was this intentional?
>  How are you using the --quiet option and why would you even need it?
I used
git show --quiet --pretty="format:%ci" HEAD
to extract the commit date of HEAD, and I simply replaced it with
git log -1 --quiet --pretty="format:%ci" HEAD
Though, the email from Junio suggests I should use (and this works)
git show -a --pretty="format:%ci" HEAD
still, I wonder if there is no better/more efficient solution to this.
/Gustaf
Carlos Martín Nieto· May 29, 2011, 13:24 UTC · re: Gustaf Hendeby · lore

Re: git show and the --quiet option

On Sat, May 28, 2011 at 08:03:50PM +0200, Gustaf Hendeby wrote:
Show 26 quoted lines
> Hi Carlos,
> 
> thanks for the detailed answer.
> 
> On 05/28/2011 07:26 PM, Carlos Martín Nieto wrote:
> > On Sat, May 28, 2011 at 06:53:28PM +0200, Gustaf Hendeby wrote:
> >> Hello everyone,
> >>
> >> I was playing around with "git show" lately and realized it has changed
> >> its behavior regarding the --quiet option, which no longer suppresses
> >> the diff output as it used to.  The behavior change happened in
> >> 1c40c36b ("log: convert to parse-options").  Was this intentional?
> >  How are you using the --quiet option and why would you even need it?
> 
> I used
> 
> git show --quiet --pretty="format:%ci" HEAD
> 
> to extract the commit date of HEAD, and I simply replaced it with
> 
> git log -1 --quiet --pretty="format:%ci" HEAD
> 
> Though, the email from Junio suggests I should use (and this works)
> 
> git show -a --pretty="format:%ci" HEAD
> 
I'm assuming you meant -s instead of -a
> still, I wonder if there is no better/more efficient solution to this.
> 
There is --format, so that line would look like
    git show -s --format="%ci" HEAD

which IMO is quite compact and self-explanatory. Depending on how much control you have over the environment, you could set up an alias like

    git config alias.show-commit 'show -s'
or even
    git config alias.show-commit-date 'show -s --format="%ci"'
   cmn
-- 
Carlos Martín Nieto | http://cmartin.tk

"¿Cómo voy a decir bobadas si soy mudo?" -- CACHAI
Junio C Hamano· May 28, 2011, 19:17 UTC · re: Carlos Martín Nieto · lore

Re: git show and the --quiet option

Carlos Martín Nieto <cmn@elego.de> writes:
Show 10 quoted lines
>> 1c40c36b ("log: convert to parse-options").  Was this intentional?
>
> Very much so.
>> ...
> The long answer is that the log family (and git-format-patch, which
> is where this started) never actually accepted --quiet, so it would
> get passed down to the diff machinery. This (for complicated reasons
> I'm not sure I comletely understand, but that have to do with the
> internal handling of 'quiet' as 'quick') caused every second commit
> not to show.

Yes, "git format-patch" that gives empty patch for every other commit would have been incorrect, but "--quiet" to squelch patch output, especially in the context of "show" whose default is to show patch, is something people would naturally expect, even though admittedly it was doing so by accident.

How does this patch look?

It does not fix "git show master~10 master^..master", but instead of just hijacking and ignoring the --quiet option like your patch did, it actually flips the option the user wanted to affect from the command line.

 builtin/log.c |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)
diff --git a/builtin/log.c b/builtin/log.c
index 27849dc..224b167 100644
--- a/builtin/log.c
+++ b/builtin/log.c
@@ -107,6 +107,8 @@ static void cmd_log_init_finish(int argc, const char **argv, const char *prefix,
 			     PARSE_OPT_KEEP_DASHDASH);
 
 	argc = setup_revisions(argc, argv, rev, opt);
+	if (quiet)
+		rev->diffopt.output_format |= DIFF_FORMAT_NO_OUTPUT;
 
 	/* Any arguments at this point are not recognized */
 	if (argc > 1)
Carlos Martín Nieto· May 30, 2011, 09:32 UTC · re: Junio C Hamano · lore

Re: git show and the --quiet option

On Sat, May 28, 2011 at 12:17:40PM -0700, Junio C Hamano wrote:
Show 24 quoted lines
> Carlos Martín Nieto <cmn@elego.de> writes:
> 
> >> 1c40c36b ("log: convert to parse-options").  Was this intentional?
> >
> > Very much so.
> >> ...
> > The long answer is that the log family (and git-format-patch, which
> > is where this started) never actually accepted --quiet, so it would
> > get passed down to the diff machinery. This (for complicated reasons
> > I'm not sure I comletely understand, but that have to do with the
> > internal handling of 'quiet' as 'quick') caused every second commit
> > not to show.
> 
> Yes, "git format-patch" that gives empty patch for every other commit
> would have been incorrect, but "--quiet" to squelch patch output,
> especially in the context of "show" whose default is to show patch, is
> something people would naturally expect, even though admittedly it was
> doing so by accident.
> 
> How does this patch look?
> 
> It does not fix "git show master~10 master^..master", but instead of just
> hijacking and ignoring the --quiet option like your patch did, it actually
> flips the option the user wanted to affect from the command line.

It's fine if that's what we want to do. The reason I blocked --quiet instead of converting it to -s is because it seemed less surprising than passing --quiet and still getting output (if I pass --quiet, I'd expect the application to really be quiet), which doesn't happen in the commands that accept --quiet on purpose. Then again, the log family doesn't make any sense without any output, so if you argue that way, --quiet means "quieter", which makes the interface less consistent, but I don't feel that strongly about it

So sure, if you think it helps, apply it. 
Show 22 quoted lines
> 
>  builtin/log.c |    2 ++
>  1 files changed, 2 insertions(+), 0 deletions(-)
> 
> diff --git a/builtin/log.c b/builtin/log.c
> index 27849dc..224b167 100644
> --- a/builtin/log.c
> +++ b/builtin/log.c
> @@ -107,6 +107,8 @@ static void cmd_log_init_finish(int argc, const char **argv, const char *prefix,
>  			     PARSE_OPT_KEEP_DASHDASH);
>  
>  	argc = setup_revisions(argc, argv, rev, opt);
> +	if (quiet)
> +		rev->diffopt.output_format |= DIFF_FORMAT_NO_OUTPUT;
>  
>  	/* Any arguments at this point are not recognized */
>  	if (argc > 1)
> --
> To unsubscribe from this list: send the line "unsubscribe git" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
> 
Drew Northup· Jun 2, 2011, 18:26 UTC · re: Carlos Martín Nieto · lore

Re: git show and the --quiet option

On Mon, 2011-05-30 at 11:32 +0200, Carlos Martín Nieto wrote:
> On Sat, May 28, 2011 at 12:17:40PM -0700, Junio C Hamano wrote:
> > Carlos Martín Nieto <cmn@elego.de> writes:
> > 
Show 14 quoted lines
> > How does this patch look?
> > 
> > It does not fix "git show master~10 master^..master", but instead of just
> > hijacking and ignoring the --quiet option like your patch did, it actually
> > flips the option the user wanted to affect from the command line.
> 
> It's fine if that's what we want to do. The reason I blocked --quiet
> instead of converting it to -s is because it seemed less surprising
> than passing --quiet and still getting output (if I pass --quiet, I'd
> expect the application to really be quiet), which doesn't happen in
> the commands that accept --quiet on purpose. Then again, the log
> family doesn't make any sense without any output, so if you argue that
> way, --quiet means "quieter", which makes the interface less
> consistent, but I don't feel that strongly about it

There's a lot of stuff out there for which --quiet does not imply --silent. I side with Junio on the solution.

-- 
-Drew Northup
________________________________________________
"As opposed to vegetable or mineral error?"
-John Pescatore, SANS NewsBites Vol. 12 Num. 59
Carlos Martín Nieto· Jun 5, 2011, 23:13 UTC · re: Drew Northup · lore

Re: git show and the --quiet option

On Thu, Jun 02, 2011 at 02:26:09PM -0400, Drew Northup wrote:
Show 23 quoted lines
> 
> On Mon, 2011-05-30 at 11:32 +0200, Carlos Martín Nieto wrote:
> > On Sat, May 28, 2011 at 12:17:40PM -0700, Junio C Hamano wrote:
> > > Carlos Martín Nieto <cmn@elego.de> writes:
> > > 
> 
> > > How does this patch look?
> > > 
> > > It does not fix "git show master~10 master^..master", but instead of just
> > > hijacking and ignoring the --quiet option like your patch did, it actually
> > > flips the option the user wanted to affect from the command line.
> > 
> > It's fine if that's what we want to do. The reason I blocked --quiet
> > instead of converting it to -s is because it seemed less surprising
> > than passing --quiet and still getting output (if I pass --quiet, I'd
> > expect the application to really be quiet), which doesn't happen in
> > the commands that accept --quiet on purpose. Then again, the log
> > family doesn't make any sense without any output, so if you argue that
> > way, --quiet means "quieter", which makes the interface less
> > consistent, but I don't feel that strongly about it
> 
> There's a lot of stuff out there for which --quiet does not imply
> --silent. I side with Junio on the solution.
Then don't let me stop you.
   cmn
-- 
Carlos Martín Nieto | http://cmartin.tk

"¿Cómo voy a decir bobadas si soy mudo?" -- CACHAI
Junio C Hamano· May 28, 2011, 17:55 UTC · re: Gustaf Hendeby · lore

Re: git show and the --quiet option

Gustaf Hendeby <hendeby@isy.liu.se> writes:
> I was playing around with "git show" lately and realized it has changed
> its behavior regarding the --quiet option, which no longer suppresses
> the diff output as it used to.

The official and right way to suppress diff output from "show" has always been with the "-s" option, and it should still work. Otherwise please report a bug here.

Thanks.
Junio C Hamano· May 28, 2011, 18:27 UTC · re: Junio C Hamano · lore

Re: git show and the --quiet option

Junio C Hamano <gitster@pobox.com> writes:
Show 7 quoted lines
>> I was playing around with "git show" lately and realized it has changed
>> its behavior regarding the --quiet option, which no longer suppresses
>> the diff output as it used to.
>
> The official and right way to suppress diff output from "show" has always
> been with the "-s" option, and it should still work. Otherwise please
> report a bug here.
Having said that, I think this is a minor regression.

"git show A B C" has been about showing objects (not commits) A and B and C. It picks a convenient format for human consumption for each type, and shows commit as if it were given to "log -1 -p", tree as if it were given to "ls-tree --name-only", blob as if it were given to "cat-file blob".

But recently, Linus bolted "git show A..B" on to it, and in a way that is quite wrong. It walks the history by accident, not by design. This makes fixing this regression somewhat complex, I suspect.

Given the existing machinery to "show" each individual object given from the command line, one would naturally imagine that we have a routine that takes one object, tells its object type, and formats the object in the representation suitable for human consumption, and have a loop over the command line to call that routine with each object from the command line. And "git show A..B" would first walk to find individual commit objects between A and B, and feed the same routine with these commits one by one.

Not so. The current implementation walks the history between A..B as a side effect of showing a commit (starting from B) and works by pure accident.

Case in point: "git show master master" shows two copies of the same commit, as it should. "git show master^..master master" does not. The reason? Walking between "master^..master" is done as a side effect of showing "master^..master" and marks commit object "master" already shown, and makes the command ignore the second argument.

A worse example can be seen by running something silly like "git show master~10 master^..master", which you would expect to see two commits (master~10 and master). Do not do this on anything with a deep history like the kernel repository---it will walk down to the root commit.

I think the ideal fix would be to fix the "show A..B" support (one possible solution would be to simply disable it, but I'd see it as the last resort) so that it first collects the commit objects in a queue by properly walking (and clean the object flags that were used to control the walking after we know what commits are in the range), expand A..B into these commits on the command line arguments list, and then run the resulting command line arguments through the traditional "git show" machinery that shows one object at a time.

If we go that route, then we should always use "quiet" during the internal history walking that expands A..B to the set of commits in the range with or without command line --quiet. And then make both --quiet and -s from the command line to control if the patch is shown when showing a commit.

← back to recent threads