同じソフトウェアが開発されている 2 つのリポジトリがあるとします。1つは顧客に出荷されるレガシーバージョンで、バグは修正されています。そしてもう 1 つは、同じソフトウェアの非常に見事な書き直しであり、A でうまくいかなかったすべてのものが今では素晴らしく輝いています (そうです…)。
そのため、時間が経ち、何らかの理由である時点で、書き換えが成功したと見なされます。レガシー ソフトウェアを廃止することにしました。ただし、2 つのリポジトリの必要性を取り除きながら、その履歴を保持したいと考えています (念のため…)。
リポジトリ A が次のようになっているとします。
A---B---C
/ \
D---E---F---G---H---I master (A)
偶然にも、リポジトリ B は次のようになります。
S---R---Q
/ \
K---L---M---N---O---P master (B)
だから、私たちがやりたいのはタイプすることだけです
[~/repo-a]$ git magic
結果としてこれを取得します。
A---B---C S---R---Q
/ \ / \
D---E---F---G---H---I---K---L---M---N---O---P master (A)
ただし、残念git-magic
ながらコマンドはありません (目的を達成するためのコマンド)。
私がこれまでに試したことは、
a]
git-rebase
マージ戦略のマニュアルページを見ると、ours
私たちが望んでいたようです
私たちのもの
これにより任意の数のヘッドが解決されますが、マージの結果のツリーは常に現在のブランチ ヘッドのツリーになり、他のすべてのブランチからのすべての変更が効果的に無視されます。これは、サイドブランチの古い開発履歴に取って代わるために使用されることを意図しています。これは、再帰的マージ戦略に対する -Xours オプションとは異なることに注意してください。
[~/repo-a]$ git remote add shiny-rewrite git@github.com/orga/shiny-rewrite.git
[~/repo-a]$ git fetch shiny-rewrite
[~/repo-a]$ git checkout shiny-rewrite/master
[~/repo-a]$ git checkout -b shiny-master
[~/repo-a]$ git rebase -s ours master
First, rewinding head to replay your work on top of it...
Already applied: 0001 initial commit
Already applied: 0002 blablabla
Already applied: 0003 …
Already applied: 0004 ZOMG IT'S READY
All done.
ただし、shiny-rewrite からのコミットはすべてなくなりました。まさに私たちが望んでいたものではありません。
b]
「ブルートフォース」の代替手段
[~/repo-a]$ git rm -r *
[~/repo-a]$ git commit -am "DELETE ALL THE THINGS"
[~/repo-a]$ git remote add shiny-rewrite git@github.com/orga/shiny-rewrite.git
[~/repo-a]$ git fetch shiny-rewrite
[~/repo-a]$ git checkout shiny-rewrite/master
[~/repo-a]$ git checkout -b shiny-master
[~/repo-a]$ git rebase master
[~/repo-a]$ git checkout master
[~/repo-a]$ git merge shiny-master
しかし、今、この削除コミットがあります..
A---B---C S---R---Q
/ \ / \
D---E---F---G---H---I---X---K---L---M---N---O---P master (A)
/\
||
"DELETE ALL THE THINGS"