GitのRebaseがいまだによくわからない

概念は理解できるんだが、想定通りに行かない

 

履歴を残さずに、差分を取り込もうと思って、

作業中のブランチで以下を行った

git pull --rebase origin master

 

想定通り、履歴を残さずに差分を取り込めた

 

しかし、作業中ブランチにpushしたところエラーになった

error: failed to push some refs to 'git@github.com:xxxxxx/xxxxxxxx.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. Integrate the remote changes (e.g.
hint: 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.

 

 

というわけで元に戻した

Git 間違って rebase しちゃったのを元に戻したい - かもメモ

git log

git status

git reflog

git reset --hard HEAD@{26}

 

 

 

リベースについて、もう一度学ぶ。

 

git pull と git pull –rebase の違いって?図を交えて説明します! – KRAY Inc.

 

以下引用

 

git fetch

リモートのコピーちょうだい

 

git merge master 

ローカルリポジトリのmasterの内容を自分に取り込む

 

origin/ブランチ名 はリモート追跡ブランチのこと

 

git rebase

マージと違ってリベースの場合はコミットを新しく作りなおすので、リベース前とはコミット自身の id と親の id が変わります

親のidが変わると、すでにリモートリポジトリにブランチをプッシュしていた場合、リモートにあるブランチの親の id が一致せずプッシュできなくなり(rejectされ)ます。

 

git pull

git pull origin master = git fetch + git merge origin/master

 

 

 

git rebaseのちょっとしたまとめ - Chiroru's Diary

現在いるブランチを、rebaseしてきたブランチの先頭にくっつける

 

この時、現在いるブランチのコミットを一瞬退避(一時保存)し、rebaseしてきたブランチに現在いるブランチをgit reset --hardして、保存していたコミットを上にのせる仕組みです。


リベースを行うとコミットのidが変わり、別物として扱われます。これはコミットが新しく作られるためであり、リモートリポジトリに既にpushしていた場合は、ローカルと一致しなくなってしまいpushできなくなります。

 

 

 

困ったときの git reset コマンド集 - Qiita

ワーキングツリー : 最新のファイル状態
インデックス : コミットするためのファイル状態
ローカルリポジトリ : ファイルの変更履歴を記録(ローカル環境)
リモートリポジトリ : ファイルの変更履歴を記録(共有できる)

 

git add : 「ワーキングツリー → インデックス」
git commit : 「インデックス → ローカルリポジトリ
git push : 「ローカルリポジトリ → リモートリポジトリ」

 

reset --hard :add、commit、ワーキングツリーの取り消し
reset --mixed:commitとaddの取り消し。
reset --soft :commitのみ取り消し。

 

HEAD

最新のコミットの状態を表している
@でも表現ができる : HEAD = @
^ や ~ をつけることで直前のコミットを表すことができる : HEAD^ 、 HEAD~

 


直前のコミットをなかったことにする
git reset --soft HEAD^

 

直前のコミットを取り消し
git reset --hard HEAD^

 

コミット後の変更を全部消したい
git reset --hard HEAD

 

addを取り消したい
git reset --mixed HEAD

 

git resetをなかったことにする
git reset --hard ORIG_HEAD

 

 

 

まぁ結局のところ、リベースはいまいちよくわからない。

以下が説明になるんだろうが。

 

現在いるブランチを、rebaseしてきたブランチの先頭にくっつける

この時、現在いるブランチのコミットを一瞬退避(一時保存)し、rebaseしてきたブランチに現在いるブランチをgit reset --hardして、保存していたコミットを上にのせる仕組みです。

リベースを行うとコミットのidが変わり、別物として扱われます。これはコミットが新しく作られるためであり、リモートリポジトリに既にpushしていた場合は、ローカルと一致しなくなってしまいpushできなくなります。

 

 

どういう時に使えばいいのかよくわからない。

同時進行してるものを計画的に結合する作業の時は、「計画的に」使えば有りだと思うが、日常の作業で全エンジニアが使うものとしては微妙な気がする。

というか、リスクが大きい気がする。