たまに忘れるので、自分にもわかりづらい適当なメモを残します。
##基本
用語 | 概念 |
---|---|
GIT | 警察、検察 |
リポジトリ | 国 |
ファイル | 人間 |
ファイルの変更 | 犯罪 |
アントラッキングファイル | 不法入国者 |
アンモディファイドファイル | カタギ |
モディファイドファイル | 被疑者 |
ステージドファイル | 被告人 |
コミット | 服刑 |
ブランチ | 前科 |
ステージング | 裁判所 |
##逮捕&起訴
$ git add <Filename>
$ git add . # 全部
$ git add -p # 対話式で選択
##判決
$ git commit -m 'commit message' # 判決理由が入る
##強制送還
$ rm <filename> # 普通に削除
$ git clean -f # 先に--dry-run で確認すると酔い
##免罪、誤認逮捕、不起訴
$ git rm <filename>
$ git mv <filename>
$ git reset <filename> # addしたindexにあるfileをindexから除外
$ git reset --hard HEAD^
$ git reset --hard <commit hash> # 刑の免除
$ git revert <commit hash> # 逆位相
$ git rebase -i # タイムリープ
$ git checkout <commit hash>
処分保留?
$ git stash list
$ git stash save -u <message> # アントラッキングも含める
$ git stash apply <stash number>
$ git stash drop <stash number>
$ git stash clear # 全消し
比較系
$ git diff
$ git diff --cached
$ git diff HEAD HEAD^
##取り調べ
$ git status
$ git status --short
##実刑の確認
$ git show <commit name>
##前科の確認
$ git log
$ git log --graph --date=short --format='%C(yellow)%h%C(reset) %C(magenta)[%ad]%C(reset)%C(red)%d%C(reset) %s %C(cyan)@%an%C(reset)' # aliasのやつ
マージ系
$ git merge <branchname> # 現在のブランチに別のブランチをマージ
$ git push -f # プルリク歴史修正の時の強制プッシュ
$ git push origin <local branchname> # 現在のブランチをリモートにマージ
$ git pull origin <remote branchname> # リモートのブランチを現在のブランチにマージ
$ git fetch # originの今のブランチの変更履歴を取得 --allだと全てのブランチ
$ git mergetool
ブランチ刑
$ git reflog # ブランチの操作ログ
$ git checkout -b <branchname> # ブランチを作成してチェックアウト
$ git branch -a # 全部ブランチ名の確認
$ git branch -r # リモート全部ブランチ名の確認
$ git branch -v # 詳細表示
$ git branch -d <branchname> # ローカルのを削除
$ git push origin :<branchname> # リモートに削除
$ git fetch
$ git checkout master
$ git merge origin/master
タグとか
$ git tag # tag一覧
$ git tag <tagname> # タグ付け
$ git -d <tagname> # ローカルのタグ削除
$ git push origin :<tagname> # リモートに削除
$ git push origin --tags # タグ全部送信
最初にやること
$ git init # 一から作る
$ git remote add origin git@<ssh hostname>:<myname>/<reponame>.git
$ touch README.md
$ git add .
$ git commit -m 'init'
$ git push -u origin master
$ git clone # 他人のパクる
不法入国者へ戻す
$ git rm --cached "filename"
$ echo "filename" >> .gitignore
submodule
$ git submodule add https://github.com/twbs/bootstrap.git bootstrap
$ git submodule update # 内部submoduleを同期する
後からgitignoreに追加
$ echo "hoge.tmp" >> .gitignore
$ git rm --cached hoge.tmp
リベース
マージとリベースの違い
※Gitは共通の祖先のコミットから比較してdiffを出している。
$ # 下図だと、共通の親はCなのでCからFまでの変更点(EとDへ変更した内容)としてまとめられる
$ checkout master && git merge topic
$ # 下図だと、共通の親はEなのでEからD'までの変更点(Dで変更した内容)としてまとめられる
$ checkout topic && git rebase master
プルリクが別のプルリクに依存する場合のプルリクの作り方
$ git fetch --all # リモートのブランチ一覧取得
$ git checkout develop # developブランチは派生元にしたいブランチ(このブランチはmasterから派生していおり、変更が今後ありそうにないブランチ、プルリクではLGTM済み)
$ git checkout feature # developブランチから新たなfeatureを作成する
$ # featureブランチのプルリク作成
$ git commit -m "追加" # featureに追加する
$ # developのプルリクがmasterにマージされた
$ git fetch --all # リモートのブランチ一覧取得
$ git checkout feature
$ git rebase develop # featureブランチの上で最新のdevelopにrebaseする
$ git push origin feature -f # フォースプッシュでプルリクの履歴を書き換える
プルリクのコミットをキレイにする(rebase squash)
$ git rebase -i <commit hash> # 修正したいコミットの一つ前のコミットのハッシュを指定する(0d4a808の前のコミットを指定する)
pick 9a54fd4 commitの説明を追加 # <- この中で一番古いのコミット
squash 0d4a808 pullの説明を追加 # <- これをsオプションで上のコミットと混ぜられる
# Rebase 326fc9f..0d4a808 onto d286baa
#
# 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
#
# If you remove a line here THAT COMMIT WILL BE LOST.
# However, if you remove everything, the rebase will be aborted.
#
$ git push origin hoge -f
$ # もしcannot squash without a previous commitが出た場合
$ git rebase --abort
プルリクの過去のコミットを変更する(rebase edit)
- 空のコミットメッセージと内容のcommitがある場合は下手に
$ git rebase -i <commit hash> # 修正したいコミットの一つ前のコミットのハッシュを指定する(0d4a808の前のコミットを指定する)
pick 9a54fd4 commitの説明を追加 # <- この中で一番古いのコミット
edit 0d4a808 pullの説明を追加 # <- このコミットでの変更内容を再変更する
# Rebase 326fc9f..0d4a808 onto d286baa
#
# 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
#
# If you remove a line here THAT COMMIT WILL BE LOST.
# However, if you remove everything, the rebase will be aborted.
#
$ vim hoge.js
$ git add hoge.js # 変更を追加
$ git commit --amend # コミットに追加する
$ git rebase --continue # コミットを適用する
$ git push origin hoge -f
リベースのマージ
$ git rebase branch
// コンフリクトしたファイルを修正後
$ git add conflicted_file
$ git commit
$ git rebase --continue
$ git rebase --abort // ダメそうだったら
スタッシュ
コマンドをよく忘れるが次を見ればいい。
https://qiita.com/akasakas/items/768c0b563b96f8a9be9d
コンフリクト解消
$ git pull origin master # コンフリ発生!!
$ git reset --hard ORIG_HEAD # マージを元にもどす
リベース前のブランチからの派生した新ブランチを、リベース済みの元ブランチへのリベースする方法
- develop > feature > hotfix の順で派生しておりhotfixがfeatureの機能に依存している
- featureをdevelopでrebaseした(その結果featureのコミット番号が全部変わった)
- bugfixをfeatureでrebaseしようとするとconflictが発生した(しかも、diffがめちゃくちゃ)
$ git push origin hotfix # rebase前のhotfixのバックアップ
$ git checkout hotfix
$ git rebase --onto feature ff34ed1 # featureを元にしたff34ed1に続くcommitを持つhotfixのブランチを作る
$ # つまり、
$ # - ff34ed1は古いfeature(リベースされる前)の最後のcommit番号。
$ # - つまり、hotfixのPRのコミットログにあるfeatureの最後のCommit番号
$ # - 別の言い方をすればhotfixブランチの元のcommit番号
$ # - featureオプションはもちろん新しいrebase済みのブランチを指す
First, rewinding head to replay your work on top of it...
Applying: AAAAAAAA #31
Applying: XXXXXXX #31
Applying: VVVVVVV #31
$ git diff master --stat # hotfixのPRのdiffとくらべて同じなら多分大丈夫
6 files changed, 251 insertions(+), 3 deletions(-)
つまり、rebaseされた元のブランチfeaturに、
rebaseされる前のfeatureの最後のcommit(hotfixの元のcommit)を足したということ
リベース前のブランチからの派生した新ブランチ(マージコミット済み)を、リベース済みの元ブランチへのリベースする方法
master > feature > hotfix の順でhotfixはfeatureからrebaseで切った。
ただし、masterが別のブランチ(feature2)でマージされ、歴史が進められたので、featureブランチとfeature2ブランチでconflictした
そこで、featureブランチをmasterでmergeし、マージコミットをfeatureブランチに作って、conflictを解消した
その後、featureブランチはmasterブランチにマージした(mergeコミットありで)
hotfixはfeatureから切られているので、featureに再rebaseしたが、hotfixの修正内容が反映されていない。
その時は、hotfixをmasterブランチでmergeして解消するのが良い。
同一ファイルを分割してCommit
$ git add -p
y or n or q...
$ git diff --cached # the diff between staging and HEAD
あるファイルをあるコミット/ブランチの前に戻す
$ git checkout c5f567~1 -- file_a.py file_b.py
--no-ff --no-commit
参考文献
脳
🍏さん
https://liginc.co.jp/web/tool/79390
http://www.backlog.jp/git-guide/stepup/stepup7_5.html
https://stackoverflow.com/questions/27445747/how-to-rebase-over-already-rebased-branch
https://stackoverflow.com/questions/1587846/how-do-i-show-the-changes-which-have-been-staged