git rebase -i
するとこのようなメッセージが表示されると思います。これらの動作についてです。
# Commands:
# p, pick = use commit
# r, reword = use commit, but edit the commit message
# e, edit = use commit, but stop for amending
# s, squash = use commit, but meld into previous commit
# f, fixup = like "squash", but discard this commit's log message
# x, exec = run command(the rest of the line) using shell
# d, drop = remove commit
こなみにこれらは、一旦指定コミットまで戻った上で上(古いコミット)から下(新しいコミット)に処理されていきます。
p, pick
デフォルトではこれになっていると思いますが、これはそのままそのコミット内容を再適用するということになります。
r, reword
これを指定したコミットの適用前にエディターが開いてコミットメッセージを変更できます。
e, edit
そのコミットをgit commit --amend
したあとの状態で待機させます。git status
を実行すると以下のようになります。
You can amend the commit now, with
git commit --amend
Once you are satisfied with your changes, run
git rebase --continue
何かやりたいなら再度git commit --amend
などで取り入れ、git rebase --continue
で次のコミットへ移動します。
これはそのコミットのauthor
情報の書き換えがしたいような場合に便利なモードです。
s, squash
そのコミットのメッセージとpush
内容をを一つ前のコミットに含ませ、この単体のコミットはなかった事にします。
例えば以下のような履歴だとします。
git diff HEAD~1 --name-only
# a.js
git log --oneline | sed -n 1p
# 977fa06fc add b.js
git diff HEAD~2 --name-only
# b.js
git log --oneline | sed -n 2p
# 90490591b add a.js
そしてgit rebase -i HEAD~2
を実行して以下のように編集してから閉じます。
pick 977fa06fc add a.js
s 90490591b add b.js
すると以下のようなまとめるコミットのメッセージ編集が立ち上がるので、適当に閉じます。
# This is a combination of 2 commits.
# This is the 1st commit message:
add a.js
# This is the commit message #2:
add b.js
...
f, fixup
squash
と似てますが、そのコミットのpush
内容だけが対象です。メッセージは単に捨てられます。
また、rebase
後のコミットのメッセージ編集も立ち上がりません。
x, exec
完全にやり直したい場合に使えます。そのコミット内容を完全に捨ててしまい、やりたければまったく新しいコミットをその場で作成・適用ができます。このコマンドの実行時にはそのタイミングで待機状態になります。以下はそのときのgit status
の例です。
git status
# interactive rebase in progress; onto 02063c9
# Last commands done (3 commands done):
# pick 18819b7 foo
# exec bcac294 bar
# (see more in file .git/rebase-merge/done)
# Next command to do (1 remaining command):
# pick 403a6aa baz
# You are currently editing a commit while rebasing branch 'master' on '02063c9'.
# (use "git commit --amend" to amend the current commit)
# (use "git rebase --continue" once you are satisfied with your changes)
nothing to commit, working tree clean
「いいタイミングでgit rebase --continue
してください」とあります。何もせずにそれを実行すると次のセクションのd, drop
を適用した時と同じになります。「元コミットに無を適用した」ということで何もなかったことにしたような感じです。
このタイミングのソースの状態は、このx, exec
を適用する前の状態です。例えば、ある時点からあるバグが起こるようになってしまいその検証の為に、「怪しいある時点に戻って、その時の状態でチェックしていく」ような時に使えると思います。(そしてgit rebase --abort
。。。)
d, drop
単にそのコミットを削除します。
これはたまにmaster
を経由しなければいけないのに、平行で作業中のブランチから新しいブランチと移動してしまい作業中だったブランチの内容を持ってきてしまった時にブランチを作り直さなくても良くなったりします。
allow-empty は表示されない
これを調べる時に--allow-empty
コミットを作って確認しようと思ったのですが、一覧に表示されませんでした。駄目みたいですね。