push.defaultにmatchingを設定しない方が良い理由

こないだのHokkaido.pm Casual#12で、Gitを使ったデモ中に、
warning: push.default is unsetが出る件について書くことになったけど、
ちょっとカジュアルじゃなかったので、これまでいくつかの記事を書いてきました。

という訳で、説明に必要なGitの使い方について一通り書けたと思うので、
“push.default”の値を”matching”にした場合に都合が悪い例を使って、
説明してみたいと思います。

まずは、フォルダ構成から。

.
├── Repo # git init --bareで初期化
└── Work

次に、git cloneを実行してローカルリポジトリを初期化します。
$ cd ../Work
$ git clone ../Repo .
$ git remote
origin

そして、masterブランチで作業して、一段落を終えたことにします。
$ echo aaa >> readme.txt
$ git add readme.txt
$ git commit -m "初回コミット"

ここまでの作業をリモートリポジトリにも反映します。
$ git push

ここまでが、今回の準備作業です。

では、”push.default”の値を”simple”に設定します。
$ git config push.default simple
$ git config push.default
simple

今回は、git configで設定するときに--globalを付けていないので、
このリポジトリでのみ適用される”push.default”の値を設定します。
もし、興味があれば、”.git/config”の中身を見てください。
“push.default”の設定が記述されているのを確認することが出来ます。

次に、機能追加に相当する作業を行います。
$ echo bbb >> readme.txt
$ git commit -a -m "bbbを追加"
[master 0900e79] bbbを追加
1 file changed, 1 insertion(+)

ここで、急ぎのお願いが入ったとして、
新しいブランチを作成して、そこで作業を行います。
$ git checkout -b topic origin/master
Branch topic set up to track remote branch master from origin.
Switched to a new branch 'topic'
$ cat readme.txt
aaa

topicブランチ作成時にorigin/masterを指定している理由は、
すでに共有リポジトリで公開済みのmasterブランチをベースに作業を行うためです。

そして、topicブランチでの作業を終えて、
topicブランチを共有リポジトリにプッシュします。
$ echo ccc >> readme.txt
$ git commit -a -m "cccを追加"
[topic 0d120f5] cccを追加
1 file changed, 1 insertion(+)
$ git push -u origin topic

これで、共有ブランチにtopicブランチが追加されて、
-uを追加したことで、topicブランチでgit pushのみ実行した場合は、
共有ブランチにできたtopicブランチにプッシュされるようになりました。

では、試しに以下のコマンドを実行してみます。
$ git push
Everything up-to-date

ここまでは、期待した通りの結果ですね。

次に、”push.default”の値を”matching”に変更します。
$ git config push.default matching
$ git config push.default
matching

そして、もう一度、git pushを実行してみます。
$ git push
Counting objects: 5, done.
Writing objects: 100% (3/3), 266 bytes, done.
Total 3 (delta 0), reused 0 (delta 0)
To ../Repo
a7cb0e5..0900e79 master -> master

何が起きたか分かりますか?
git guiを使って、すべてのリポジトリの履歴を見てみましょう。

“push.default”の値が”matching”だったので、
ローカルリとリモートリポジトリで双方に名前が一致するブランチが存在する場合、
その一致するブランチすべてで、

$ git push origin <一致するブランチ名>

が行われました。

現在、ローカルとリモートにmasterブランチとtopicブランチが存在していて、
masterブランチには、まだプッシュされていないコミットが存在していたため、
今回はそれがプッシュされてしまったのです。

ついでなので、以下の操作も試してみましょう。
$ echo ddd >> readme.txt
$ git commit -a -m "dddを追加"
[topic a468266] dddを追加
1 file changed, 1 insertion(+)
$ cat readme.txt
aaa
ccc
ddd
$ git checkout master
Switched to branch 'master'
$ cat readme.txt
aaa
bbb
$ git push
Counting objects: 5, done.
Writing objects: 100% (3/3), 270 bytes, done.
Total 3 (delta 0), reused 0 (delta 0)
To ../Repo
0d120f5..a468266 topic -> topic

という訳で、masterブランチに切り替えてgit pushしたにも関わらず、
topicブランチの方がプッシュされてしまいました。

ここまでを理解した上で、
warning: push.default is unsetが出る件について」を、
もう一度、読んで頂ければと思います。

あと、このリポジトリにおける”push.default”の設定を削除するには、
以下のコマンドを実行します。
$ git config --unset push.default

おしまい。

Leave a Comment