コマンド@Git¶
はじめに¶
本サイトにつきまして、以下をご認識のほど宜しくお願いいたします。
add¶
--all¶
変更した全てのファイルをaddする。
branch¶
branch --all¶
作業中のローカルブランチとリモート追跡ブランチを取得する。
branch -M¶
現在のブランチを新しい名前に変更する。
$ git branch -M main
clone¶
認証¶
▼ HTTPS接続¶
Basic認証でGitHubにログインし、クローンする。
GitHubのユーザー名とパスワードが必要になる。
$ git clone https://github.com/<組織名>/<GitHubリポジトリ名>.git
ユーザー名とパスワードの入力は、ターミナルに手動で入力する方法と、自動的に入力する方法がある。
後者の場合、1
個目にURLに設定する方法がある。
$ git clone https://<ユーザー名>:<パスワード>@github.com/<組織名>/<GitHubリポジトリ名>.git
もう1
個の方法として、~/.netrc
ファイルに定義しておく。
machine github.com
login <ユーザー名>
password <パスワード>
▼ SSH公開鍵認証¶
SSH公開鍵認証でGitHubにログインし、クローンする。
GitHubの自身の公開鍵を登録する必要がある。
サーバー接続名は、SSH公開鍵認証の設定ファイル (~/.ssh/config
) に記載されている。
デフォルトでは、GitHubの接続名は、『github.com
』になっている。
$ git clone git@<ssh-configファイルでのサーバー接続名>:<組織名>/<GitHubリポジトリ名>.git
▼ アクセストークン¶
アクセストークンを使用して、クローンする。
$ git clone https://<ユーザー名>:<トークン>@github.com/<GitHubリポジトリ名>.git
オプション¶
▼ 名前指定¶
リポジトリのクローンを別名でクローンする。
# fooという名前でクローン
$ git clone https://github.com/hiroki-hasegawa/foo-repository.git foo
▼ --recursive¶
リポジトリがサブモジュールを含む場合、サブモジュールも合わせてクローンする。
$ git clone --recursive https://github.com/hiroki-hasegawa/foo-repository.git
▼ --depth¶
最近コミットのみをクローンする。
処理速度が求められる場合 (例:CIの実行コンテナなど) に役立つ。
$ git clone --depth 1 https://github.com/hiroki-hasegawa/foo-repository.git
config¶
設定の影響範囲の種類¶
影響範囲 | 意味 | 上書き順 | 設定ファイルの場所 |
---|---|---|---|
system | 全PCユーザーの全リポジトリ | 1 | /etc/gitconfig |
global | 現在のPCユーザーの全リポジトリ | 2 | ~/.gitconfig |
local | 現在のリポジトリ | 3 | <GitHubリポジトリ名>/.git/config |
--<影響範囲>
--list¶
指定した影響範囲で適用されている設定値を取得する。--local
で設定されていない項目は、--global
の設定値が適用される。
$ git config --local --list
Macでは、1
個のマシンで2
個のGutHubアカウントを使用する場合、キーチェーンという機能で設定が必要になる。
--<影響範囲>
user.name¶
AuthorとCommitterの名前を設定する。
local
が一番最後に上書きされ、適用される。
$ git config --local user.name "hiroki.hasegawa"
--<影響範囲>
user.email¶
AuthorとCommitterのメールアドレスを設定する。
local
が一番最後に上書きされ、適用される。
$ git config --local user.email "example@gmail.com"
Authorの情報は、コミット時に反映される (Committerは表示されない) 。
$ git log
commit ee299250a4741555eb5027ad3e56ce782fe90ccb
Author: hiroki.hasegawa <example@gmail.com>
Date: Sat Sep 12 00:00:00 2020 +0900
add ◯◯を実装した。
--global core.autocrlf¶
改行コードを、特定のタイミングで自動変換するように設定する。
input
としておくのが良い。
$ git config --global core.autocrlf <値>
設定値 | チェックアウト時 | コミット時 |
---|---|---|
input | 変換しない | CRLF ➡︎ LF |
true | LF ➡︎ CRLF | CRLF ➡︎ LF |
false | 変換しない | 変換しない |
--global core.editor¶
gitのデフォルトエディタを設定する。
ここでは、Vimをデフォルトとする。
$ git config --global core.editor "vim -c "set fenc=utf-8""
init¶
initとは¶
ローカルマシンのディレクトリとGitHubリポジトリを紐付ける。
エディタにGitHubリポジトリを再反映するためにも使用できる。
$ git init
GitHubへの公開鍵の登録方法¶
GitHubとSSH公開鍵認証を実行するために、秘密鍵と公開鍵は次の方法で作成し、GitHubアカウント設定画面のSSHの項目に登録する。
(1)
-
ssh-keygen
コマンドで、秘密鍵と効果鍵のセットを作成する。
# 鍵を保管するディレクトリに移動
$ cd ~/.ssh/github
$ ssh-keygen -t rsa
# 秘密鍵と公開鍵の名前はGitHubのユーザー名にしておくとわかりやすい
Enter file in which to save the key: hiroki-it
# 鍵の使用時にパスワードの入力を要求するか否かは任意である。
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
(2)
-
このうち、公開鍵をクリップボードにコピーする。
# Mac
$ pbcopy < ~/.ssh/github/<鍵名>.pub
# Windows
$ clip < ~/.ssh/github/<鍵名>.pub
(3)
-
コピーした公開鍵を、GitHubアカウント設定画面のSSHの項目 ( https://github.com/settings/ssh ) にペーストする。
ssh
コマンドで接続を確認する。
$ ssh -T <接続名>
Hi hiroki.hasegawa! You've successfully authenticated, but GitHub does not provide shell access.
ignore¶
global ignore¶
gitignore
ファイルとして、~/.config/git/ignore
ファイルを作成する。
このgitignore
ファイルで指定したファイルは、グローバルにバージョン管理から無視される。
# IDEA
*.idea/*
# VSCode
*.code-workspace
.vscode/
# Mac
*.DS_Store
remote¶
add origin¶
プライベートリポジトリのURLを登録し、プッシュ/プル可能にする。
*実行例*
Basic認証の場合、以下の通りである。
$ git init
# Basic認証
$ git remote add origin https://github.com/hiroki-hasegawa/example.git
# 登録されたGitHubリポジトリ
remote.origin.url=https://github.com/hiroki-hasegawa/example.git
*実行例*
SSH公開鍵認証の場合、以下の通りである。
$ git init
# SSH公開鍵認証
$ git remote add origin git@github.com:<組織名またはgitユーザー名>/<GitHubリポジトリ名>.git
# 登録されたGitHubリポジトリ
remote.origin.url=git@github.com:<組織名またはgitユーザー名>/<GitHubリポジトリ名>.git
set-url origin¶
プライベートリポジトリのURLを変更し、プッシュ/プル可能にする。
config
ファイルに記述されたユーザー名と接続名を設定する。
1
個のマシンで複数のGitHubアカウントを使用している場合、設定が必須である。
プロジェクトをクローンした時、SSH URLはデフォルトで『git@github.com:<組織名またはgitユーザー名>/<プロジェクト名>.git
』となっている。
使用頻度の高いアカウントで所有するリポジトリでは、SSH URLを変更することが手間なので接続名を『github.com
』としておく。
一方で、使用頻度の低いアカウントで所有するリポジトリでは、標準のSSH URLを異なる接続名で再設定する。
*実行例*
Basic認証の場合、以下の通りである。
# Basic認証
$ git remote set-url origin https://github.com/hiroki-hasegawa/example.git
# 登録されたGitHubリポジトリ
remote.origin.url=https://github.com/hiroki-hasegawa/example.git
$ git config --local --list
# 変更されたURL
remote.origin.url=https://github.com/hiroki-hasegawa/example.git
*実行例*
SSH公開鍵認証の場合、以下の通りである。
# SSH公開鍵認証
# 使用頻度の高いアカウントで所有するリポジトリ
$ git remote set-url origin git@github.com:<組織名またはgitユーザー名>/<GitHubリポジトリ名>.git
# 使用頻度の低いアカウントで所有するリポジトリ
$ git remote set-url origin git@<任意の接続名>:<組織名またはgitユーザー名>/<GitHubリポジトリ名>.git
$ git config --local --list
# 変更されたURL
remote.origin.url=git@<任意の接続名>:<組織名またはgitユーザー名>/<GitHubリポジトリ名>.git
# 使用頻度の高いアカウント
Host github.com
User git
Port 22
HostName github.com
IdentityFile <秘密鍵へのパス>
# 使用頻度の低いアカウント
Host <任意の接続名>
User git
Port 22
HostName github.com
IdentityFile <秘密へのパス>
# その他Gitlabなど
Host gitlab.com
User git
Port 22
HostName gitlab.com
IdentityFile <秘密へのパス> # GitHabとは別の鍵を作成した方が良い。
リポジトリに対してコミットをプッシュし、エラーが出た場合、異なる接続名が選択されている場合は、URLの『接続名』の部分が正しく設定されているか否かを確認する。
$ git push
ERROR: Permission to hiroki-hasegawa/*****.git denied to Foo.
fatal: Could not read from remote repository.
Please make sure you have the correct access rights
and the repository exists.
submodule¶
サブモジュールとは¶
リポジトリ内の特定のディレクトリで他のリポジトリをリモート参照可能にする。
フォークと似た仕組みであり、git submodule update
コマンドを実行しないと、サブモジュールの更新を取り込めない。
また、git clone
コマンドの実行時には--recursive
オプションを有効化しないと、サブモジュールも合わせてクローンできない。
そのため、更新頻度の高いリポジトリをサブモジュールにすると、取り込む作業が大変になる。
add¶
カレントディレクトリにサブモジュールを作成する。
$ git submodule add --branch main https://github.com/hiroki-hasegawa/foo-sub-module.git ./modules/foo-sub-module
コマンドを実行すると、.gitmodules
ファイルが作成される。
[submodule "modules/foo-sub-module"]
path = modules/foo-sub-module
url = https://github.com/hiroki-hasegawa/foo-sub-module.git
branch = main
update¶
参照先のリポジトリで更新があった場合、それを取り込む。
参照先の更新を自動的に取り込むことはできないため、以下のコマンドを必要なタイミングで実行する必要がある。
上記を実行すると、サブモジュールのコミット情報が更新されて差分が生じるため、それをプッシュする。
$ git submodule update --remote <.gitmodulesに定義されたサブモジュール名>
--contains¶
現在にいるブランチを取得する。
$ git branch --contains
* main
--delete --force¶
プッシュとマージの状態に関係なく、ローカルブランチを削除する。
$ git branch --delete --force <ローカルブランチ名>
--move¶
作業中のローカルブランチの名前を変更する。
$ git branch --move <ローカルブランチ名>
--delete --remote¶
$ git branch --delete --remote origin/<ローカルブランチ名>
リモート追跡ブランチを削除する。
(1)
-
まず、
branch --all
で作業中のローカルブランチとリモート追跡ブランチを取得する。
$ git branch --all
* main
remotes/origin/2019/Symfony_Nyumon/main
remotes/origin/main
(2)
-
remotes/origin/2019/Symfony_Nyumon/main
を削除する。
$ git branch -d -r origin/2019/Symfony_Nyumon/main
Deleted remote-tracking branch origin/2019/Symfony_Nyumon/main (was 18a31b5).
(3)
-
再び、
branch --all
で削除されたことを確認。
$ git branch --all
* main
remotes/origin/main
checkout -b¶
指定のコミットから新しいブランチを生やせる。
$ git branch checkout -b <新しいローカルブランチ名> <コミット番号>
$ git checkout -b feature/3 d7e49b04
cherry-pick¶
cherry-pickとは¶
現在のブランチに対して、指定したコミットそれ単体をマージする。
$ git cherry-pick <コミットID>
*例*
$ git cherry-pick 1d0ddeb9e52
プルリクエストのマージによるマージコミットを指定すると、そのプルリクエストで変更されたファイルのみがコミットの内容として取得できる。
これにより、develop
ブランチ上の必要な変更のみをリリースできる。
ただし、マージコミットを指定する時は-m
オプションを有効化しないとエラーになってしまうことに注意する。
また、マージコミットには2
個の親がおり、マージ先の基点ブランチで変更されたファイルが被るコミットと作業ブランチの最後のコミットである。
前者は1番、また後者は2番となっており、1番を選択すること。
# mainブランチ上でreleaseブランチを作成し、チェックアウトする
$ git checkout -b release
# mオプションがないとエラー
$ git cherry-pick d7e49b04
error: commit d7e49b04 is a merge but no -m option was given.
fatal: cherry-pick failed
# mオプションを有効化する
$ git cherry-pick -m 1 d7e49b04
[main a9ebcb4] Merge pull request #276 from feature/123
Author: hiroki.hasegawa <*****@users.noreply.github.com>
Date: Wed Sep 15 00:00:00 2021 +0900
1 file changed, 7 insertions(+)
# 指定したコミットのみがマージされているか否かを確認する。
$ git log
# releaseブランチをmainブランチにマージする。
$ git checkout main
$ git merge release
diff¶
結果に応じた終了コードをを出力する。
空文字をtrue
として判定する。
too many arguments
のエラーにならないように、ダブルクオーテーションをつける。
DIFF=$(git diff origin/main --name-only --relative ./...)
# 空文字かどうかを検証する
if [ -z "$DIFF" ] ; then
echo "差分なし";
exit 0
fi
echo "差分あり";
空文字でないことをtrue
として判定することもできる。
ダブルクオーテーションをつける。
DIFF=$(git diff origin/main --name-only --relative ./...)
# 空文字でないかどうかを検証する
if [ -n "$DIFF" ] ; then
echo "差分あり";
exit 1
fi
echo "差分なし";
EXIT_CODE=$(git diff origin/main --quiet)
# 終了コードを検証する
case $EXIT_CODE in
0) echo "差分なし" ;;
1) echo "差分あり" ;;
128) echo "パラーメーターが誤っている" ;;
*) echo "予期せぬエラー" ;;
esac
stash¶
stashとは¶
ファイルが、『インデックス』 (=add
) あるいは『HEAD』 (=コミット) に存在している状態で、異なるローカルブランチをcheckout
しようとすると、以下のエラーが出る。
$ git checkout 2019/Symfony2_Ny
umon/main
error: Your local changes to the following files would be overwritten by checkout:
app/config/config.yml
src/AppBundle/Entity/Inquiry.php
Please commit your changes or stash them before you switch branches.
Aborting
この場合、一度stash
を行い、『インデックス』 (=add
) あるいは『HEAD』 (=コミット) を横に置いておく必要がある。
--include-untracked¶
トラッキングされていないファイルも含めて、全てのファイルを退避させる。
git status
をしたところ、修正ファイルが3
個、トラックされていないファイルが1
個ある。
$ git status
On branch 2019/foo-repository/feature/6
Your branch is up to date with "origin/2019/foo-repository/feature/6".
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: app/Resources/views/Inquiry/index.html.twig
modified: app/config/config.yml
modified: src/AppBundle/Entity/Inquiry.php
Untracked files:
(use "git add <file>..." to include in what will be committed)
app/Resources/views/Toppage/menu.html.twig
no changes added to commit (use "git add" and/or "git commit -a")
これを、stash -u
する
$ git stash -u
Saved working directory and index state WIP on 2019/foo-repository/feature/6: 649995e update #6 *****
これらのファイルの変更点を一時的に退避できる。
-- <パス>¶
特定のディレクトリやファイルのみstash
できる。
git stash -- ./
list¶
退避している『ファイル番号ブランチ親コミットとコミットメッセージ』の一覧を取得する。
$ git stash list
stash@{0}: WIP on 2019/foo-repository/feature/6: 649995e update #6 *****
pop¶
退避している指定のファイルを復元する。
$ git stash pop stash@{<番号>}
$ git stash pop stash@{0}
On branch 2019/foo-repository/feature/8
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: app/Resources/views/Inquiry/index.html.twig
modified: app/config/config.yml
modified: src/AppBundle/Entity/Inquiry.php
Untracked files:
(use "git add <file>..." to include in what will be committed)
app/Resources/views/Toppage/menu.html.twig
no changes added to commit (use "git add" and/or "git commit -a")
drop¶
退避している指定のファイルを復元せずに削除する。
$ git stash drop stash@{<番号>}
$ git stash drop stash@{0}
Dropped refs/stash@{0} (1d0ddeb9e52a737dcdbff7296272080e9ff71815)
clear¶
退避している全てのファイルを復元せずに削除する。
$ git stash clear
status¶
statusとは¶
addステージやcommitステージにファイルが存在しているか否かを取得する。
--porcelain¶
git status
コマンドを他のコマンドに入力できる形式で出力する。
CIの自動化で使用することが多い。
$ git status --porcelain
M foo
M bar
M baz
#!/bin/bash
git add .
if [ -z "$(git status --porcelain)" ]; then
echo "変更点がないため、終了しました。"
exit 0;
fi
git commit -m "CIツールが自動的にプッシュしました。"
git pull
git push origin HEAD
revert¶
revertとは¶
作業中のローカルブランチで、指定の履歴を削除する。
<コミットID>
--no-edit¶
指定したコミットのみを打ち消す新しいコミットを作成する。
コミットメッセージは、打ち消すコミットと同じものになる。
リリース後に元に戻したい時に役立つ。
$ git revert <コミットID> --no-edit
<コミットID>
--edit¶
指定したコミットのみを打ち消す新しいコミットを作成する。
vimが起動するため、コミットメッセージを新しいものに変更する。
$ git revert <コミットID> --edit
-m <マージナンバー> <マージコミットID>¶
指定したマージコミットのみを打ち消す新しいコミットを作成する。
コミットメッセージは、打ち消すコミットと同じものになる。
マージナンバーを事前に確認しておく必要がある。
$ git show
commit xyz
Merge: 1a1a1a 2b2b2b #ここに注目
Author: xxxx xxxx
Date: Thu Jul 13 09:00:00 2017 +0000
Merge commit
$ git revert -m 1 xyz
reset¶
resetとは¶
作業中のローカルブランチで、指定の履歴まで戻し、それ以降を削除する。
HEAD <ファイル名/パス>¶
インデックスから、指定したファイルを削除する。
$ git reset HEAD <ファイル名/パス>
--soft <コミットID>¶
作業中のブランチで、最新のHEAD (=コミット後) を指定の履歴まで戻し、それ以降を削除する。
コミットのみを取り消したい場合はこれ。
$ git reset --soft <コミットID>
--mixed <コミットID>¶
作業中のローカルブランチで、インデックス (=add
後) 、HEAD (=コミット後) を指定の履歴まで戻し、それ以降を削除する。
add
とコミットを取り消したい場合はこれ。
$ git reset --mixed <コミットID>
--hard <コミットID> (ブランチ)¶
作業中のローカルブランチで、最新のワークツリー (=ディレクトリ) 、インデックス (=add
後) 、HEAD (=コミット後) を指定の履歴まで戻し、それ以降を削除する。
ワークツリー (=ディレクトリ) 内のファイルの状態も戻ってしまうため、取り扱い注意!!
$ git reset --hard <コミットID>
$ git reset --hard <ブランチ名>
resetの使用例¶
(1)
-
まず、
log
コマンドで、作業中のローカルブランチにおけるコミットIDを確認。
$ git log
commit f17f68e287b7d84318b4c49e133b2d1819f6c3db (HEAD -> main, 2019/foo-repository/main)
Merge: 41cc21b f81c813
Author: hiroki.hasegawa <example@gmail.com>
Date: Wed Mar 20 22:56:32 2019 +0900
Merge remote-tracking branch "refs/remotes/origin/main"
commit 41cc21bb53a8597270b5deae3259751df18bce81
Author: hiroki.hasegawa <example@gmail.com>
Date: Wed Mar 20 20:54:34 2019 +0900
add #0 fooさんのREADME_2を追加
commit f81c813a1ead9a968c109671e6d83934debcab2e
Author: hiroki.hasegawa <example@gmail.com>
Date: Wed Mar 20 20:54:34 2019 +0900
add #0 fooさんのREADME_1を追加
(2)
-
指定のコミットまで履歴を戻す。
$ git reset --soft f81c813a1ead9a968c109671e6d83934debcab2e
(3)
-
log
コマンドで、正しく変更されているか確認。
$ git log
commit f81c813a1ead9a968c109671e6d83934debcab2e (HEAD -> main)
Author: Hiroki Hasegawa <example@gmail.com>
Date: Wed Mar 20 20:54:34 2019 +0900
add 新しいREADMEを追加
(4)
-
push --force
でローカルリポジトリの変更をリモートリポジトリに強制的に反映する。 『強制的にプッシュした』というログも、リモート側には残らない。
$ git push --force
Total 0 (delta 0), reused 0 (delta 0)
To github.com:hiroki-hasegawa/foo-repository.git
+ f0d8b1a...f81c813 main -> main (forced update)
強制的にpullする¶
$ git reset --hard origin/<ブランチ名>
rebase¶
rebaseとは (注意点あり)¶
作業中のローカルブランチで、ブランチの派生元を変更する。
例えば、作業ブランチで基点ブランチのコミットを取り込みたい場合に使用する。
リモートブランチにプッシュした後は使用してはならず、他のコマンドを使用する。
処理結果がgit merge
コマンドと似ているが、git rebase
コマンドはマージコミットを作らず、ない。
--interactive <コミットID>¶
派生元を変更する機能を応用して、過去のコミットのメッセージ変更、削除、統合などを実行する。
*例 (コミットメッセージの変更) *
(1)
-
まず、
log
コマンドで、作業中のローカルブランチにおけるコミットIDを確認。
$ git log
commit f17f68e287b7d84318b4c49e133b2d1819f6c3db (HEAD -> main, 2019/foo-repository/main)
Merge: 41cc21b f81c813
Author: Hiroki Hasegawa <example@gmail.com>
Date: Wed Mar 20 22:56:32 2019 +0900
Merge remote-tracking branch "refs/remotes/origin/main"
commit 41cc21bb53a8597270b5deae3259751df18bce81
Author: Hiroki Hasegawa <example@gmail.com>
Date: Wed Mar 20 20:54:34 2019 +0900
add #0 fooさんのREADME_2を追加
commit f81c813a1ead9a968c109671e6d83934debcab2e
Author: Hiroki Hasegawa <example@gmail.com>
Date: Wed Mar 20 20:54:34 2019 +0900
add #0 fooさんのREADME_1を追加
(2)
-
指定した履歴の削除
$ git rebase --interactive 41cc21bb53a8597270b5deae3259751df18bce81
とすると、タブが表示され、指定のコミットIDの履歴が表示される
pick b1b5c0f add #0 *****
『挿入モード』に変更し、この1行のpick
をedit
に変更。
その後、
:w
として保管。
その後、エディタ上で『Ctrl+C』を押し、
:qa!
で終了。
(3)
-
git commit --amend
に-m
オプションを付けて、メッセージを変更する。
$ git commit --amend -m="<変更後のメッセージ>"
(4)
-
git rebase --continue
コマンドを実行することにより、変更を反映させる。
$ git rebase --continue
Successfully rebased and updated refs/heads/develop.
(5)
-
プッシュしようとすると、
![rejected] develop -> develop (non-fast-forward)
とエラーが出るため、
$ git merge <ブランチ名> --allow-unrelated-histories
で解決し、プッシュする。
*例 (Author名とCommiter名の変更) *
(1)
-
ハッシュ値を指定して、
git rebase
コマンドを実行する。
$ git rebase --interactive 41cc21bb53a8597270b5deae3259751df18bce81
(2)
-
git commit --amend
コマンドに--reset-author
オプションを付けて、configで設定した名前をAuthor名とComitter名に適用する。
$ git commit --amend --reset-author
(3)
-
git rebase --continue
コマンドを実行し、変更を反映させる。
$ git rebase --continue
Successfully rebased and updated refs/heads/develop.
過去の全てのコミットに対して、Author名とCommitter名を適用するコマンドもある。
しかし、危険な方法であるため、個人利用のリポジトリのみで使用するようにする必要がある。
#!/bin/bash
git filter-branch -f --env-filter "
# Author名かCommitter名のいずれかが誤っていれば適用します。
if [ ${GIT_AUTHOR_NAME}="hiroki.hasegawa" -o ${GIT_COMMITTER_NAME}="hiroki.hasegawa" ] ; then
export GIT_AUTHOR_NAME="hiroki.hasegawa"
export GIT_AUTHOR_EMAIL="example@gmail.com"
export GIT_COMMITTER_NAME="hiroki.hasegawa"
export GIT_COMMITTER_EMAIL="example@gmail.com"
fi"
--onto <派生元にしたいローカルブランチ名> <誤って派生元にしたローカルブランチ名> <派生元を変更したいローカルブランチ名>¶
作業中のローカルブランチの派生元を変更する。
$ git rebase --onto <派生元にしたいローカルブランチ名> <誤って派生元にしたローカルブランチ名> <派生元を変更したいローカルブランチ名>
--interactive --root¶
一番古い、最初の履歴を削除する。
(1)
-
変更タブの表示
$ git rebase --interactive --root
とすると、最初の履歴が記述されたタブが表示される
pick b1b5c0f add #0 *****
(2)
-
pick b1b5c0f add #0 *****
の行を削除して保管し、タブを閉じ、エディタ上で『Ctrl+C』を押す。
:qa!
ここで未知のエラー
CONFLICT (modify/delete): README.md deleted in HEAD and modified in 37bee65... update #0 README.mdに本レポジトリのタイトルと引用を記載した
した. Version 37bee65... update #0 README.mdに本レポジトリのタイトルと引用を記載した of README.md left in tree.
error: could not apply 37bee65... update #0 README.mdに本レポジトリのタイトルと引用を記載した
Resolve all conflicts manually, mark them as resolved with
"git add/rm <conflicted_files>", then run "git rebase --continue".
You can instead skip this commit: run "git rebase --skip".
To abort and get back to the state before "git rebase", run "git rebase --abort".
Could not apply 37bee65... update #0 README.mdに本レポジトリのタイトルと引用を記載した
--abort¶
やりかけのrebase
を取り消し。
作業中のローカルブランチにおける(main|REBASE-i)
が、(main)
に変更されていることからも確認可能。
hiroki.hasegawa@PC /var/www/foo (main)
$ git rebase --interactive
hiroki.hasegawa@PC /var/www/foo (main|REBASE-i)
$ git rebase --abort
hiroki.hasegawa@PC /var/www/foo (main)
$
pull¶
コマンド組み合わせ¶
全てのリモートブランチをpullする。
$ git branch -r \
| grep -v "\->" \
| grep -v main \
| while read remote; do git branch --track "${remote#origin/}" "$remote"; done
$ git fetch --all
$ git pull --all
push¶
-u origin <作成したブランチ名>¶
ローカルで作成したブランチを、リモートにプッシュする。
コミットは無くても良い。
$ git push -u origin <作成したブランチ名>
origin <コミットID>:main¶
トラウマコマンド。
$ git push origin <コミットID>:main
--delete origin <バージョンタグ>¶
リモートブランチのタグを削除する。
$ git push --delete origin <バージョンタグ>
*例*
$ git push --delete origin v1.0.0
注意点として、ローカルマシンのタグは別に削除する必要がある。
$ git tag -d v1.0.0
--tags¶
ローカルマシンのコミットに付与したタグをリモートにプッシュする。
$ git push --tags
show-branch¶
作業ブランチの派生元になっているブランチを確認。
$ git show-branch \
| grep "*" \
| grep -v "$(git rev-parse --abbrev-ref HEAD)" \
| head -1 \
| awk -F"[]~^[]" "{print $2}"
filter-branch¶
-f --env-filter¶
指定した名前とメールアドレスを上書きする。
$ git filter-branch --force --env-filter '
# GIT_AUTHOR_NAMEの書き換え
if [ "$GIT_AUTHOR_NAME"="<変更前のコミッター名>" ];
then
GIT_AUTHOR_NAME="<変更後のコミッター名>";
fi
# GIT_AUTHOR_EMAILの書き換え
if [ "$GIT_AUTHOR_EMAIL"="<変更前のコミッターメールアドレス>" ];
then
GIT_AUTHOR_EMAIL="<変更後のコミッターメールアドレス>";
fi
# GIT_COMMITTER_NAMEの書き換え
if [ "$GIT_COMMITTER_NAME"="<変更前のコミッター名>" ];
then
GIT_COMMITTER_NAME="<変更後のコミッター名>";
fi
# GIT_COMMITTER_EMAILの書き換え
if [ "$GIT_COMMITTER_EMAIL"="<変更前のコミッターメールアドレス>" ];
then
GIT_COMMITTER_EMAIL="<変更後のコミッターメールアドレス>";
fi
' -- --all
-f --tree-filter¶
全てのコミットに対して、指定した処理を実行する。
*例*
全てのコミットに対して、特定のファイルを削除する処理を実行する。
加えて、ローカルリポジトリに対してガーベジコレクションを実行すると、ローカルリポジトリから完全に削除できる。
$ git filter-branch -f --tree-filter \
'rm -f <パス>' \
HEAD
# ガベージコレクションを実行する
$ git gc --aggressive --prune=now