壁球的第一次两次提交在Git?[重复]
-
11-09-2019 - |
题
这个问题已经有一个答案在这里:
- 结合前两次提交的个混库? 8的答案
与 git rebase --interactive <commit>
你可以壁球任何数量的承诺一起纳入一个单一的。
这是所有伟大的除非你想打壁球承诺进入初始提交。这似乎不可能做到的。
是否有任何方法来实现它吗?
适度相关:
在一个相关的问题,我设法拿出一个不同的方法来需要的胚对第一承诺,这是,嗯,使它的第二个。
如果你有兴趣: 文件怎么插入一个提交第一、转移所有其他人吗?
解决方案
更新月2012(git1.7.12+)
你现在可以重订,所有提交的最根本和选择第二个承诺 Y
被压扁的第一个 X
.
git rebase -i --root master
pick sha1 X
squash sha1 Y
pick sha1 Z
git rebase [-i] --root $tip
这个命令现在可以用于所有改写历史上领先从"
$tip
"下的根本承诺。
看看 提交df5df20c1308f936ea542c86df1e9c6974168472上。 从 克里斯*韦伯(arachsys
).
原来的答复(2009年)
我相信你会发现不同的食谱,在这样的问题"我如何相结合的第一次两次提交的个混库?"
查尔斯*贝利 提供有最大的 详细的回答, ,提醒我们这一承诺是一个完整的树(不仅仅是比较从前一个国)。
和这里的老commit("初始提交")和新的承诺(结果的挤压)将没有任何共同的祖先。
这意味着你不能"commit --amend
"初始提交入新的一个,然后衍合到新的初始提交的历史,以前的初始承诺(许多冲突)
(最后一句是不再真实的 git rebase -i --root <aBranch>
)
而不是(与 A
原来的"初始承诺", B
随后提交需要压扁成最初的一个):
回到最后提交的,我们希望的形式的初始提交(分离头):
git checkout <sha1_for_B>
重置分支指针向初始提交,但留下的指数和工作树不变:
git reset --soft <sha1_for_A>
修改初始树木用树'B':
git commit --amend
临时标记这一新的初始提交(或者你可以记住新的承诺sha1手动):
git tag tmp
回到原来的分支(假定掌握这个例):
git checkout master
重放所有提交后的B到新的初始提交:
git rebase --onto tmp <sha1_for_B>
删除临时标记:
git tag -d tmp
这种方式,"rebase --onto
"不引入冲突期间合并,因为它rebases历史 后 最后一次提交(B
)被压扁成最初的一个(这是 A
)来 tmp
(代表的被压扁的新初次提交):琐碎快进合并只。
那工作对"A-B
",但也"A-...-...-...-B
"(任何数量的承诺可以被压扁的成最初的一个这种方式)
其他提示
我已经重新设计VonC的脚做的一切自动和不要问我任何东西。你给这两个提交SHA1s,它将壁球之间的一切成一个他们提交的名为"被压扁的历史":
#!/bin/sh
# Go back to the last commit that we want
# to form the initial commit (detach HEAD)
git checkout $2
# reset the branch pointer to the initial commit (= $1),
# but leaving the index and working tree intact.
git reset --soft $1
# amend the initial tree using the tree from $2
git commit --amend -m "squashed history"
# remember the new commit sha1
TARGET=`git rev-list HEAD --max-count=1`
# go back to the original branch (assume master for this example)
git checkout master
# Replay all the commits after $2 onto the new initial commit
git rebase --onto $TARGET $2
为什么它的价值,避免这个问题总是创建一个"禁运"的第一承诺,其唯一的在该仓库是空的。gitignore:
https://github.com/DarwinAwardWinner/git-custom-commands/blob/master/bin/git-myinit
这样,从未有任何理由的混乱与第一提交。
如果你只是想压制所有提交到一个单一、初始提交的,只是重置库和修订第一个承诺:
git reset hash-of-first-commit
git add -A
git commit --amend
Git重置将离开的工作树完整,所以一切都是仍然存在。所以就增加该文件令添加命令,而修订的第一个提交这些变化。相比变基-我你会失去能力合并从初意见。
这将壁球第二提交到的第一个:
A-B-C-... -> AB-C-...
git filter-branch --commit-filter '
if [ "$GIT_COMMIT" = <sha1ofA> ];
then
skip_commit "$@";
else
git commit-tree "$@";
fi
' HEAD
提交信息AB将从B(虽然我喜欢从一)。
具有同样的效果如Uwe克莱-柯尼希的答案,但适用于非最初的一个。
挤压的第一和第二承诺将导致在第一个承诺正在改写。如果你有多于一个分支,这是基于第一承诺,你要剪掉那的分支。
考虑下面的例子:
a---b---HEAD
\
\
'---d
挤压a和b入一个新的提交"ab"将导致在两个不同的树木,在大多数情况下是不可取的,因为 混帐合并 和 混帐变基 将不再工作跨越两个分支机构。
ab---HEAD
a---d
如果你真的想要这个,这是可以做到的。看看 混帐过滤器的分支 对于一个强大的(危险)的工具,为历史重写。
你可以偏滤分支。例如
git filter-branch --parent-filter \
'if test $GIT_COMMIT != <sha1ofB>; then cat; fi'
这种结果在a-b-C扔掉的提交日志的A.
你可以使用的变基互动式的修改的最后两个提交之前,他们已经被推到一个遥
git rebase HEAD^^ -i
有一个简单的方法来做到这一点。让我们假设你是对的 master
支
创建一个新的孤立分支,这将删除所有提交的历史:
$ git checkout --orphan new_branch
添加初始提交信息:
$ git commit -a
摆脱旧未并入的主分支机构:
$ git branch -D master
重新命名你的当前分支 new_branch
要 master
:
$ git branch -m master