[解決済み] リベースの後、同じブランチに Git のコミットが複製される
質問
Pro Git で提示されたシナリオは、以下の通りです。 リベースの危険性 . 著者は基本的に、重複したコミットを避ける方法を教えてくれます。
公開リポジトリにプッシュしたコミットをリベースしないでください。
私の特殊な状況をお話します。Pro Gitのシナリオとはちょっと違うようですが、それでも重複したコミットをしてしまうことがあるからです。
例えば、2つのリモートブランチと、それに対応するローカルブランチがあるとします。
origin/master origin/dev
| |
master dev
4つのブランチにはすべて同じコミットが含まれており、私はこれから
dev
:
origin/master : C1 C2 C3 C4
master : C1 C2 C3 C4
origin/dev : C1 C2 C3 C4
dev : C1 C2 C3 C4
数回コミットした後、その変更を
origin/dev
:
origin/master : C1 C2 C3 C4
master : C1 C2 C3 C4
origin/dev : C1 C2 C3 C4 C5 C6 # (2) git push
dev : C1 C2 C3 C4 C5 C6 # (1) git checkout dev, git commit
に戻らねばならない。
master
をクリックすると、すぐに修正できます。
origin/master : C1 C2 C3 C4 C7 # (2) git push
master : C1 C2 C3 C4 C7 # (1) git checkout master, git commit
origin/dev : C1 C2 C3 C4 C5 C6
dev : C1 C2 C3 C4 C5 C6
そして、戻る
dev
私は、実際の開発にクイックフィックスを含めるために変更をリベースしています。
origin/master : C1 C2 C3 C4 C7
master : C1 C2 C3 C4 C7
origin/dev : C1 C2 C3 C4 C5 C6
dev : C1 C2 C3 C4 C7 C5' C6' # git checkout dev, git rebase master
GitX/gitk でコミットの履歴を表示させると、次のようなことがわかります。
origin/dev
は、2つの同じコミットを含んでいます。
C5'
と
C6'
であり、Gitとは異なるものです。では、もし私が変更を
origin/dev
これがその結果です。
origin/master : C1 C2 C3 C4 C7
master : C1 C2 C3 C4 C7
origin/dev : C1 C2 C3 C4 C5 C6 C7 C5' C6' # git push
dev : C1 C2 C3 C4 C7 C5' C6'
Pro Gitでの説明を理解しきれていないのかもしれないので、2つほど教えていただきたいのですが。
-
なぜGitはリベースの際にこれらのコミットを重複させるのですか?を適用するだけでなく、そうする特別な理由があるのでしょうか?
C5
とC6
の後にC7
? - どうすれば回避できますか?した方が賢明でしょうか?
どのように解決するのですか?
ここでは rebase を使うべきではありません。単純なマージで十分です。リンク先の Pro Git book では、基本的にこの状況を正確に説明しています。内部構造は若干異なるかもしれませんが、私はこのように考えています。
-
C5
とC6
から一時的に引き出されます。dev
-
C7
が適用されます。dev
-
C5
そしてC6
の上に再生されます。C7
新しい差分を作成し、新しいコミットを作成します。
ということで、あなたの
dev
というブランチを作成します。
C5
と
C6
は事実上存在しなくなりました。
C5'
と
C6'
. にプッシュすると
origin/dev
の場合、git は
C5'
と
C6'
を新しいコミットとして、履歴の末尾に追加します。実際
C5
と
C5'
で
origin/dev
を見ると、内容は同じでも行番号が違うことに気づくでしょう -- つまりコミットのハッシュが違うのです。
Pro Gitのルールをもう一度説明します。 ローカルリポジトリ以外の場所に存在するコミットをリベースしてはならない . 代わりにマージを使用してください。
関連
-
[解決済み] 複数のコミットをチェリーピックする方法
-
[解決済み] Git で直近のローカルコミットを取り消すには?
-
[解決済み] Git でブランチからコミットを削除する
-
[解決済み] git rebase の取り消し
-
[解決済み] Git で現在のブランチ名を取得するには?
-
[解決済み] Gitブランチをmasterにマージする最も良い(そして最も安全な)方法は何ですか?
-
[解決済み] detached HEADとmaster/originの連携はどうすればいいですか?
-
[解決済み] git のコミットを削除しても、変更は維持できますか?
-
[解決済み] Git で最新のコミットを新しいブランチに移動する
-
[解決済み】Featureブランチのリベースの後、Gitプッシュが拒否される。
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み】マージの競合が発生した git stash pop の取り消し
-
[解決済み】git-mergeの-dry-runオプションはありますか?
-
[gitコミット失敗の解決] 現在のブランチの先端が後ろにあるため、更新が拒否されました。
-
Gitのプッシュでエラーが発生! [リモート拒否] master -> master (pre-receive hook declined) error: failed to push s...
-
[解決済み] ERROR: リモートレポ 'origin' のクローン作成に失敗しました。
-
[解決済み] TortoiseGitで「git did not exit cleanly (exit code 128)」というエラーを解決するには?[クローズド]
-
[解決済み] Git エラー : 'upstream' は git リポジトリでないようです。
-
[解決済み] git rebase: "error: cannot stat 'file': パーミッションが拒否されました"
-
[解決済み] 修正したコミットをリモートの Git リポジトリにプッシュするにはどうしたらいいですか?
-
[解決済み】Git reset --hard でリモートリポジトリにプッシュする。