All of lore.kernel.org
 help / color / mirror / Atom feed
* log -p hides changes in merge commit
@ 2011-01-06 17:07 Phillip Susi
  2011-01-06 19:43 ` Junio C Hamano
  0 siblings, 1 reply; 6+ messages in thread
From: Phillip Susi @ 2011-01-06 17:07 UTC (permalink / raw)
  To: git

git log -p never shows a diff for merge commits.  It is nice that it
does not show a giant diff that is the sum of all of the changes being
merged, but any manual changes made on top of the merge are also lost
from view, and this is not good.  Here is a reproduction recipe:

git init
echo foo > a
git add a
git commit -m "added a"
git branch other
git checkout other
echo bar > b
git add b
git commit -m "added b"
git checkout master
git merge other
git log -p

At this point there is no diff shown in the log output.  This is fine
since there were no changes needed to complete the merge, and the
addition of b is already documented in the merged commit.  The problem
is that if you add --no-merge to the git merge, and then:

echo bart > a
git add a
git commit

Now in addition to merging b, you have modified a, but git log -p still
shows no diff, effectively hiding the fact that you snuck in a
modification to a during the merge.

It seems that adding -c or --cc to the log correctly shows the change to
a, but why is this not shown by default?

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: log -p hides changes in merge commit
  2011-01-06 17:07 log -p hides changes in merge commit Phillip Susi
@ 2011-01-06 19:43 ` Junio C Hamano
  2011-01-06 20:50   ` Phillip Susi
  0 siblings, 1 reply; 6+ messages in thread
From: Junio C Hamano @ 2011-01-06 19:43 UTC (permalink / raw)
  To: Phillip Susi; +Cc: git

Phillip Susi <psusi@cfl.rr.com> writes:

> It seems that adding -c or --cc to the log correctly shows the change to
> a, but why is this not shown by default?

Depends on the definition of "correctly", but perhaps you have a
definition different from ours ;-) The "patches" shown with -c/--cc are
designed to be different from normal diff so that people do not
accidentally try to apply them with "patch" or "git apply".

"log -p" omits merge commits by default because diffs of merges are mostly
not useful for ordinary purposes.  If you are trying to use "log -p" to
reproduce a (part of) history, perhaps you would want to also study -m
option.

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: log -p hides changes in merge commit
  2011-01-06 19:43 ` Junio C Hamano
@ 2011-01-06 20:50   ` Phillip Susi
  2011-01-06 21:04     ` Jonathan Nieder
  0 siblings, 1 reply; 6+ messages in thread
From: Phillip Susi @ 2011-01-06 20:50 UTC (permalink / raw)
  To: Junio C Hamano; +Cc: git

On 1/6/2011 2:43 PM, Junio C Hamano wrote:
> Depends on the definition of "correctly", but perhaps you have a
> definition different from ours ;-) The "patches" shown with -c/--cc are
> designed to be different from normal diff so that people do not
> accidentally try to apply them with "patch" or "git apply".
> 
> "log -p" omits merge commits by default because diffs of merges are mostly
> not useful for ordinary purposes.  If you are trying to use "log -p" to
> reproduce a (part of) history, perhaps you would want to also study -m
> option.

What I would like to do is be able to review a merge to sign off on it.
 While the full diff against the left parent would be a large and
unhelpful amalgamation of the changes in the merged branch, any
additional changes made during the commit should not be hidden.  This
allows someone performing the merge to effectively sneak in unintended
changes.  I would expect any such changes to be shown by log -p, but
this only seems to happen if you add -c.

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: log -p hides changes in merge commit
  2011-01-06 20:50   ` Phillip Susi
@ 2011-01-06 21:04     ` Jonathan Nieder
  2011-01-07 19:27       ` Phillip Susi
  0 siblings, 1 reply; 6+ messages in thread
From: Jonathan Nieder @ 2011-01-06 21:04 UTC (permalink / raw)
  To: Phillip Susi; +Cc: Junio C Hamano, git

Phillip Susi wrote:

> What I would like to do is be able to review a merge to sign off on it.
>  While the full diff against the left parent would be a large and
> unhelpful amalgamation of the changes in the merged branch, any
> additional changes made during the commit should not be hidden.  This
> allows someone performing the merge to effectively sneak in unintended
> changes.  I would expect any such changes to be shown by log -p, but
> this only seems to happen if you add -c.

To be more precise, here is what -c and --cc do.  Consider the
following history (time flowing left to right):

    -- [topic]
   /
 B --- [master]

>From the master branch, I merge topic.  (1) If I am lucky, the changes
from B to topic and B to master touch entirely different sections of
code (though perhaps within the same files), so one could just apply
the two diffs in succession to make a merge automatically.  (2) Almost
as good is the case when they touch code a couple of lines apart ---
"git merge" still figures it out automatically.  (3) Less nice is the
case when they touch the same line, say --- but even here the correct
merge can be obvious.  (4) Worst of all is when the changes
semantically conflict but syntactically do not:

	$ git merge topic
	$ make test;	# fails!
	$ ... hack hack hack ...
	$ git commit --amend

   -- o [topic] ------
  /                   \
 B -- o --------------- [master]

In case (1), -c will show a "combined diff" for files where master
does not match either the old master or topic.  --cc, on the other
hand, will correctly suppress these uninteresting diffs.

In case (2), -c will show a noisy "combined diff" as before.
--cc will show a combined diff when the changes from both parents
touch nearby code, even if it merged trivially.

In case (3), -c and --cc will show the semantically boring but
syntactically interesting merge.

Case (4) is underspecified.  So let's give a more precise example:
the old master and topic tried to fix the same bug in two incompatible
ways.  When merging, I decide I like the topic's way better, so I
resolve conflicts in favor of the topic.  Hopefully all unrelated
changes on master were preserved!

In this case, -c and --cc will very likely show nothing at all.
Each file matches one of the two parents (old master or topic) so
there is no easy way to distinguish the case from (0) or (1).

By now it should be clear how to get the diff you are looking for.
One makes a test merge, perhaps using the iffy "resolve in favor
of one side or the other" feature to save time on conflicts:

	git checkout oldmaster^0
	git merge topic
	git reset --merge ORIG_HEAD; # meh, too many conflicts
	git merge -Xours topic

and then makes a diff.

	git diff master

Hope that helps,
Jonathan

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: log -p hides changes in merge commit
  2011-01-06 21:04     ` Jonathan Nieder
@ 2011-01-07 19:27       ` Phillip Susi
  2011-01-07 20:27         ` Junio C Hamano
  0 siblings, 1 reply; 6+ messages in thread
From: Phillip Susi @ 2011-01-07 19:27 UTC (permalink / raw)
  To: Jonathan Nieder; +Cc: Junio C Hamano, git

On 1/6/2011 4:04 PM, Jonathan Nieder wrote:
> In case (1), -c will show a "combined diff" for files where master
> does not match either the old master or topic.  --cc, on the other
> hand, will correctly suppress these uninteresting diffs.
> 
> In case (2), -c will show a noisy "combined diff" as before.
> --cc will show a combined diff when the changes from both parents
> touch nearby code, even if it merged trivially.
> 
> In case (3), -c and --cc will show the semantically boring but
> syntactically interesting merge.
> 
> Case (4) is underspecified.  So let's give a more precise example:
> the old master and topic tried to fix the same bug in two incompatible
> ways.  When merging, I decide I like the topic's way better, so I
> resolve conflicts in favor of the topic.  Hopefully all unrelated
> changes on master were preserved!
> 
> In this case, -c and --cc will very likely show nothing at all.
> Each file matches one of the two parents (old master or topic) so
> there is no easy way to distinguish the case from (0) or (1).

That does help me understand the difference between -c and -cc, but I
still don't see why one or the other is not the default behavior of log
-p, instead of opting to never show anything at all for merges?

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: log -p hides changes in merge commit
  2011-01-07 19:27       ` Phillip Susi
@ 2011-01-07 20:27         ` Junio C Hamano
  0 siblings, 0 replies; 6+ messages in thread
From: Junio C Hamano @ 2011-01-07 20:27 UTC (permalink / raw)
  To: Phillip Susi; +Cc: Jonathan Nieder, git

Phillip Susi <psusi@cfl.rr.com> writes:

> That does help me understand the difference between -c and -cc, but I
> still don't see why one or the other is not the default behavior of log
> -p, instead of opting to never show anything at all for merges?

Assuming this is about the default, the answer is very simple.  The
features to support -c and --cc came _much_ later than -p, and many people
have got used to the default behaviour after using "log -p" for a long
time.  It simply is rude to change the default on them.

As -c or --cc won't do anything special on a non-merge commit, you can
always say "log -p --cc" if that output is what you want to see.

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2011-01-07 20:28 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-01-06 17:07 log -p hides changes in merge commit Phillip Susi
2011-01-06 19:43 ` Junio C Hamano
2011-01-06 20:50   ` Phillip Susi
2011-01-06 21:04     ` Jonathan Nieder
2011-01-07 19:27       ` Phillip Susi
2011-01-07 20:27         ` Junio C Hamano

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.