本文共 11541 字,大约阅读时间需要 38 分钟。
先配置 git pull 命令默认为 git pull --rebase。
git config pull.rebase true
远程仓库是这样的:
本地仓库是这样的:
通过对比可以看出:
c7c56a7 是他们共同的 commit-id,但在这个节点以后,远程仓库和本地都对 hello.txt 文件进行了截然不同的修改。而且本地在修改这个文件以后,还继续进行了其他的 commit(包括对文件 hello.txt 的 commit)。
如果没有配置 'git config pull.rebase true' 而直接 git pull 的话,则会使用 merge 来处理合并(自动合并或者手动合并),但是现在我们配置了。
拉取一下:
[root@master GitTest]# git pullSuccessfully rebased and updated refs/heads/master.
虽然远程和本地都对文件进行了不同的修改,但是 rebase 合并的时候竟然没出现冲突,这是为什么呢?(因为对同一个文件的不同地方进行修改的,各自的上下文都没有发生变化,所以没有冲突)
到目前为止,远端和本地仓库的版本结构如下(本地领先远端 3 个 commit):
commit c3797b4cddb2bd43e609cefe8921c24e85fdca95 (HEAD -> master)Author: lookingDate: Tue Dec 22 09:55:31 2020 +0800 delete first line of hello.txtcommit e36200f61e20551724bf87a2afac7d338322a212Author: looking Date: Tue Dec 22 09:54:39 2020 +0800 add hello world in world.txtcommit 8cad71d41f4fb040ad9685a4a6aa039005c82ceaAuthor: looking Date: Tue Dec 22 09:51:15 2020 +0800 add nice in hello.txtcommit fb26af6981e369f1c5e29b8b8b21b1f93d3233da (origin/master)Author: looking Date: Tue Dec 22 09:49:23 2020 +0800 delete nice in hello.txtcommit c7c36a796d7a6ea5bf3c429fba88c36a61661681Author: looking Date: Tue Dec 22 09:45:56 2020 +0800 readme.txt
为了让远程仓库和本地仓库必然冲突,我在远程提交了一个 commit (清空了 hello.txt 的内容 -- 好像还不小心多加了一个空行,不过无伤大雅,目的达成就可以):
再次 git pull 一下(这次终于得偿所愿冲突了):
[root@master GitTest]# git pullremote: Enumerating objects: 3, done.remote: Counting objects: 100% (3/3), done.remote: Compressing objects: 100% (2/2), done.remote: Total 3 (delta 0), reused 0 (delta 0), pack-reused 0Unpacking objects: 100% (3/3), 865 bytes | 216.00 KiB/s, done.From github.com:2392863668/GitTest fb26af6..eced426 master -> origin/masterAuto-merging hello.txtCONFLICT (content): Merge conflict in hello.txterror: could not apply 8cad71d... add nice in hello.txtResolve all conflicts manually, mark them as resolved with"git add/rm", then run "git rebase --continue".You can instead skip this commit: run "git rebase --skip".To abort and get back to the state before "git rebase", run "git rebase --abort".Could not apply 8cad71d... add nice in hello.txt
不过先不要慌,我们先用 git status 看一下当前到底是什么情况:
[root@master GitTest]# git statusinteractive rebase in progress; onto eced426Last command done (1 command done): pick 8cad71d add nice in hello.txtNext commands to do (2 remaining commands): pick e36200f add hello world in world.txt pick c3797b4 delete first line of hello.txt (use "git rebase --edit-todo" to view and edit)You are currently rebasing branch 'master' on 'eced426'. (fix conflicts and then run "git rebase --continue") (use "git rebase --skip" to skip this patch) (use "git rebase --abort" to check out the original branch)Unmerged paths: (use "git restore --staged..." to unstage) (use "git add ..." to mark resolution) both modified: hello.txtno changes added to commit (use "git add" and/or "git commit -a")
果不其然是 hello.txt 文件冲突了(毕竟远端都把这个文件清空了,要是不冲突那才真的奇了怪)。
既然如此,那就 vim hello.txt 看一下(顺便处理一下冲突)。
[root@master GitTest]# vim hello.txt<<<<<<< HEAD=======hello worldnicehello worldhello world. I am Lookingnice to meet you too>>>>>>> 8cad71d... add nice in hello.txt
自己取舍之后进行修改(我保留的本地的版本)。
[root@master GitTest]# vim hello.txthello worldnicehello worldhello world. I am Lookingnice to meet you too
修改之后,当然要 git add hello.txt 一下:
[root@master GitTest]# git add hello.txt
现在 git status 告诉我们所有冲突都修复了之后该怎么做(甚至还告诉你了当前冲突节点的后续几个 commit 的 commit-id 和 title ):
[root@master GitTest]# git statusinteractive rebase in progress; onto eced426Last command done (1 command done): pick 8cad71d add nice in hello.txtNext commands to do (2 remaining commands): pick e36200f add hello world in world.txt pick c3797b4 delete first line of hello.txt (use "git rebase --edit-todo" to view and edit)You are currently rebasing branch 'master' on 'eced426'. (all conflicts fixed: run "git rebase --continue")Changes to be committed: (use "git restore --staged..." to unstage) modified: hello.txt
既然如此,我们就照着做一下:
[root@master GitTest]# git rebase --continue[detached HEAD b6fdaf6] add nice in hello.txt 1 file changed, 5 insertions(+), 1 deletion(-)Successfully rebased and updated refs/heads/master.
如此,便大功告成(冲突节点以后的 commit 部分仍然得以保留 --- 这可正是我想要的,我可不想每次处理完冲突就把冲突后边的 commit 重新自己写一遍):
commit 5f7be5dbb1ebe2d662efd03b7d177c2da860e0a9 (HEAD -> master)Author: lookingDate: Tue Dec 22 09:55:31 2020 +0800 delete first line of hello.txtcommit 63bb8efabbcc3759a2bd2e53d195afdaee950d62Author: looking Date: Tue Dec 22 09:54:39 2020 +0800 add hello world in world.txtcommit b6fdaf6d53a6e298ad8ab73f903e051ecd4c81e6Author: looking Date: Tue Dec 22 09:51:15 2020 +0800 add nice in hello.txtcommit eced426098acd286cb45cb7191f83ddee9cc228c (origin/master)Author: Looking <38554375+2392863668@users.noreply.github.com>Date: Tue Dec 22 10:25:57 2020 +0800 clear hello.txt
既然处理完了冲突,当然要 push 到远端一下啦:
[root@master GitTest]# git pushEnumerating objects: 12, done.Counting objects: 100% (12/12), done.Delta compression using up to 4 threadsCompressing objects: 100% (9/9), done.Writing objects: 100% (9/9), 891 bytes | 297.00 KiB/s, done.Total 9 (delta 3), reused 0 (delta 0), pack-reused 0remote: Resolving deltas: 100% (3/3), completed with 1 local object.To github.com:2392863668/GitTest.git eced426..5f7be5d master -> master
和 merge 不一样的是,rebase 处理冲突不会产生菱形框哟(可以看到,git tree 都是线性的 --- 这也是 git rebase 很受欢迎的原因之一):
先禁用 git pull 的自动 rebase:
[root@master GitTest]# git config pull.rebase false
在上面代码的基础上,将本地版本回退一个 commit:
[root@master GitTest]# git reset HEAD~Unstaged changes after reset:M hello.txt
重新修改回退版本变动的文件:
[root@master GitTest]# git diffdiff --git a/hello.txt b/hello.txtindex f4f41f3..83585f1 100644--- a/hello.txt+++ b/hello.txt@@ -1,4 +1,3 @@-hello world nice hello world
[root@master GitTest]# vim hello.txt [root@master GitTest]# git diffdiff --git a/hello.txt b/hello.txtindex f4f41f3..95696e0 100644--- a/hello.txt+++ b/hello.txt@@ -1,5 +1,5 @@-hello world nice hello world hello world. I am Looking nice to meet you too+hello world
在本地再次提交 commit :
[root@master GitTest]# git add hello.txt [root@master GitTest]# git commit -m "delete first line and add after last line for hello.txt"[master 085adcf] delete first line and add after last line for hello.txt 1 file changed, 1 insertion(+), 1 deletion(-)
从远端拉取一下:
[root@master GitTest]# git pullAuto-merging hello.txtMerge made by the 'recursive' strategy.
虽然也是对同一个文件进行的修改,但是改动地方不同,所以可以自动合并了。
[root@master GitTest]# git logcommit b2a17f4ece64a2adff17adfb0f9cfbfef24a0db7 (HEAD -> master)Merge: 085adcf 5f7be5dAuthor: lookingDate: Wed Dec 23 14:50:06 2020 +0800 Merge branch 'master' of github.com:2392863668/GitTest into mastercommit 085adcf8ee93c38b43f394f5aa8054e5478b148eAuthor: looking Date: Wed Dec 23 14:49:34 2020 +0800 delete first line and add after last line for hello.txtcommit 5f7be5dbb1ebe2d662efd03b7d177c2da860e0a9 (origin/master)Author: looking Date: Tue Dec 22 09:55:31 2020 +0800 delete first line of hello.txt
和 rebase 不一样的地方在于这儿合并的时候会多出一个 commit 而且会有明显的菱形框合并记录。
[root@master GitTest]# git log --oneline --decorate --color --graph * b2a17f4 (HEAD -> master) Merge branch 'master' of github.com:2392863668/GitTest into master|\ | * 5f7be5d (origin/master) delete first line of hello.txt* | 085adcf delete first line and add after last line for hello.txt|/ * 63bb8ef add hello world in world.txt...
我们再次把本地版本退回到远端版本的上一个版本去:
[root@master GitTest]# git reset --hard HEAD^1HEAD is now at 085adcf delete first line and add after last line for hello.txt[root@master GitTest]# git reset --hard HEAD^1HEAD is now at 63bb8ef add hello world in world.txt[root@master GitTest]# git logcommit 63bb8efabbcc3759a2bd2e53d195afdaee950d62 (HEAD -> master)Author: lookingDate: Tue Dec 22 09:54:39 2020 +0800 add hello world in world.txtcommit b6fdaf6d53a6e298ad8ab73f903e051ecd4c81e6Author: looking Date: Tue Dec 22 09:51:15 2020 +0800 add nice in hello.txt...
远端版本是在这个的基础上删掉了第一行,为了让它冲突,我们就对本地 hello.txt 文件的第一行进行修改:
[root@master GitTest]# git diffdiff --git a/hello.txt b/hello.txtindex f4f41f3..25f7272 100644--- a/hello.txt+++ b/hello.txt@@ -1,4 +1,4 @@-hello world+hello nice hello world hello world. I am Looking
然后修改 commit:
[root@master GitTest]# git add hello.txt [root@master GitTest]# git commit -m 'delete world in first line of hello.txt'[master ba8b2b1] delete world in first line of hello.txt 1 file changed, 1 insertion(+), 1 deletion(-)[root@master GitTest]# git logcommit ba8b2b1189e9a755282c5b267f2dedd76197db80 (HEAD -> master)Author: lookingDate: Wed Dec 23 15:24:02 2020 +0800 delete world in first line of hello.txtcommit 63bb8efabbcc3759a2bd2e53d195afdaee950d62Author: looking Date: Tue Dec 22 09:54:39 2020 +0800 add hello world in world.txtcommit b6fdaf6d53a6e298ad8ab73f903e051ecd4c81e6Author: looking Date: Tue Dec 22 09:51:15 2020 +0800 add nice in hello.txt...
然后从远端拉取:
[root@master GitTest]# git pullAuto-merging hello.txtCONFLICT (content): Merge conflict in hello.txtAutomatic merge failed; fix conflicts and then commit the result.
可以看到,这次自动合并失败了(毕竟远端和本地都对文件相同位置进行了不同的修改,需要手动处理冲突)。
[root@master GitTest]# vim hello.txt<<<<<<< HEADhello=======>>>>>>> 5f7be5dbb1ebe2d662efd03b7d177c2da860e0a9nicehello worldhello world. I am Lookingnice to meet you too
处理后查看状态:
[root@master GitTest]# git add hello.txt [root@master GitTest]# git statusOn branch masterYour branch and 'origin/master' have diverged,and have 1 and 1 different commits each, respectively. (use "git pull" to merge the remote branch into yours)All conflicts fixed but you are still merging. (use "git commit" to conclude merge)Changes not staged for commit: (use "git add..." to update what will be committed) (use "git restore ..." to discard changes in working directory) modified: hello.txt
保存冲突处理结果:
[root@master GitTest]# git add hello.txt[root@master GitTest]# git commit -m 'deal merge conflict in hello.txt'[master 1912baa] deal merge conflict in hello.txt
大功告成,查看并推送到远端:
commit 1912baa1b9457add393f48c41ffd35957aa8b569 (HEAD -> master)Merge: ba8b2b1 5f7be5dAuthor: lookingDate: Wed Dec 23 15:34:02 2020 +0800 deal merge conflict in hello.txtcommit ba8b2b1189e9a755282c5b267f2dedd76197db80Author: looking Date: Wed Dec 23 15:24:02 2020 +0800 delete world in first line of hello.txtcommit 5f7be5dbb1ebe2d662efd03b7d177c2da860e0a9 (origin/master)Author: looking Date: Tue Dec 22 09:55:31 2020 +0800 delete first line of hello.txt...
[root@master GitTest]# git pushEnumerating objects: 8, done.Counting objects: 100% (8/8), done.Delta compression using up to 4 threadsCompressing objects: 100% (4/4), done.Writing objects: 100% (4/4), 508 bytes | 254.00 KiB/s, done.Total 4 (delta 1), reused 0 (delta 0), pack-reused 0remote: Resolving deltas: 100% (1/1), completed with 1 local object.To github.com:2392863668/GitTest.git 5f7be5d..1912baa master -> master
当然,merge 处理合并的情况仍然是有菱形框的哟:
[root@master GitTest]# git log --oneline --decorate --color --graph * 1912baa (HEAD -> master, origin/master) deal merge conflict in hello.txt|\ | * 5f7be5d delete first line of hello.txt* | ba8b2b1 delete world in first line of hello.txt|/ * 63bb8ef add hello world in world.txt...
转载地址:http://mnjqi.baihongyu.com/