Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

git status and git diff empty after failed git am

I'm developing on a different machine than I usually do, and it seems that git is behaving differently than I remember.

When I checkout a new branch git checkout -b <new branch name>, and try to apply a patch git am </path/to/file.patch>, the patch fails to apply:

</path/to/file.patch>
Applying: <commit msg>
error: patch failed: <filename>:<line no>
error: <filename>: patch does not apply
Patch failed at <commit msg>
The copy of the patch that failed is found in: .git/rebase-apply/patch
When you have resolved this problem, run "git am --continue".
If you prefer to skip this patch, run "git am --skip" instead.
To restore the original branch and stop patching, run "git am --abort".

Now I swear on my other machines when a patch fails to apply, git status and git diff will show the file as modified with <<< HEAD >>>> markers showing where I need to fix the three way merge. Currently git status shows I'm in the middle of an am operation, but no files changed, as does git diff.

Am I mis-remembering or does my other machine maybe have an older version of git, or even a different config option set? Why does git not show a merge conflict? Do I need to set a mergetool? I don't have access to my other machine at the moment, but I'll try to update this post with more info when I can.

edit:

git am --3way seems to be what I want. [0][1] But neither git am --3way <path/to/patch> nor git config --global am.threeWay true seem to work.

ah, it's failing with a different message now:

</path/to/file.patch>
Applying: <commit msg>
fatal: sha1 information is lacking or useless (<filename>).            <-- new
error: could not build fake ancestor                                   <-- new
Patch failed at <commit msg>
The copy of the patch that failed is found in: .git/rebase-apply/patch
When you have resolved this problem, run "git am --continue".
If you prefer to skip this patch, run "git am --skip" instead.
To restore the original branch and stop patching, run "git am --abort".

Similary, git am --3way </path/to/patch> fails with:

error: patch failed: <file>:<lineno>
error: repository lacks the necessary blob to fall back on 3-way merge.
error: Makefile: patch does not apply

Maybe this patch is irredeemable? Resorting to patch -p1 < </path/to/path> applies the first hunk and fails for the second, so I guess I'll just have to do this by hand.

I should note that I'm working out of a shallow repo cloned with --depth 1.

[0] https://www.kernel.org/pub/software/scm/git/docs/git-am.html [1] https://www.kernel.org/pub/software/scm/git/docs/git-config.html

like image 279
Nick Desaulniers Avatar asked Nov 23 '16 06:11

Nick Desaulniers


2 Answers

Regarding the following error:

fatal: sha1 information is lacking or useless (<filename>).
error: could not build fake ancestor

This error can also take place when git am -3 tries to apply a patch that was generated from another repository. Workaround is to add this repository (e.g. patch-origin) for reference as:

git remote add patch-origin <path>
git fetch patch-origin

After that git should be able to build the ancestor.

like image 102
ruvim Avatar answered Oct 07 '22 00:10

ruvim


Aha! This SO post led me to an answer.

Two things going wrong:

set three way merge as the default behavior of git am:

git config --global am.threeWay true

this was confounded by the fact that I had done a shallow copy (ie. --depth 1). The SO post I linked to explains that without enough history, the warning fatal: sha1 information is lacking or useless is saying "not enough info to construct a three way merge."

It would be helpful it git mentioned in this case if you had done a shallow copy to fetch more history...

like image 32
Nick Desaulniers Avatar answered Oct 07 '22 01:10

Nick Desaulniers