Quu*_*one 13 git git-rewrite-history
我有一个包含两个分支的项目:master和gh-pages.它们本质上是两个不同的项目,其中gh-pages项目依赖于主项目(反之亦然).可以把它想象成"master包含源代码,gh-pages包含从这些源文件构建的二进制文件".我定期地接受在master中累积的更改,并使用提交消息"与主提交xxxxxxxx一致"对gh-pages分支进行新提交.
经过一段时间的这样做,我意识到,如果gh-pages提交"与主提交xxxxxxxx一致"实际上将xxxxxxxx作为其git存储库中的父项,那将会很好.像这样(糟糕的MSPaint艺术):
有没有办法让存储库看起来像上面的第二个图像?我知道如何使新的提交遵循这种模式:我可以做"git merge -s our master"(设置其他空提交的父项),然后是"git commit --amend adv550.z8"(其中adv550.z8)是实际正在改变的二进制文件).但git是否可以让您轻松回过头来为旧提交添加新父母?
一旦我让我的本地回购看起来正确,我完全愿意"git push -f"并且吹走我的Github存储库的当前历史.现在的问题是,可以让我的本地回购找吧?
编辑年后再添加:我最终放弃了尝试使git历史gh-pages
看起来像这样的尝试; 我认为零收益太过分了.我的新做法是积极地压缩提交gh-pages
,因为在我的情况下保存这些提交消息并不重要.(这只是"与主提交相符......"的长线,其中没有一个在历史上很有意思.)但是,如果我需要再次这样做,我会听到所说的答案
git merge $intended_parent_1 $intended_parent_2
git checkout $original_commit -- .
git commit --amend -a -C $original_commit
Run Code Online (Sandbox Code Playgroud)
git replace --graft $original_commit \
$(git show --pretty=%P $original_commit) \
$additional_parent
Run Code Online (Sandbox Code Playgroud)
说明: git replace --graft允许重新指定哪个是给定提交的父级.这通过编写具有相应更改的新提交并编写替换引用来工作,该替换引用使git在访问时查找新提交而不是原始提交.
git show --pretty=%P $original_commit
只列出原来的父母.
这些是你的神奇话语:
git merge origin/master --strategy ours
Run Code Online (Sandbox Code Playgroud)
在gh-pages
分支中执行此操作以记录关系,master
而不实际更改任何内容.当我创建gh-pages
分支时,这对我有用--orphan
,就像在这个答案中一样.
之后您甚至可以进行--amend
此空合并提交,以便将您实际想要进行的更改引入"页面".有关GitHub的实际示例,请参阅https://github.com/krlmlr/pdlyr/network.
您无法回到过去并更改现有的提交。即使你做了类似的事情git commit --amend
,你实际上并没有改变提交;您将在树中的同一位置创建一个新内容,其中包含原始内容(加上您的更改)的所有内容。您会注意到,提交哈希值在 后发生了变化--amend
,并且原始哈希值仍然存在于您的存储库中——您可以使用 来返回它git reflog
。
另一方面,你可以回到过去并创建另一个宇宙。本质上,您将返回到gh-pages
分支点并将整个事物(例如git cherry-pick
或其他事物)重新创建为并行分支。哈希值会改变,因为提交是不同的对象。
(我很好奇为什么你将存储库设置为单独的分支,而不是同一分支中的单独目录。似乎代码 - >构建过程会变得乏味。)