git pushでリモートリポジトリ反映済みのコミットがローカルではpushされてないことになっている

git pushで意味不明な挙動起きて困ってたけど解決したのであとで書く
大した原因ではなかったのだが、状況を言語化するのがちょっと難しくてググりづらいかもしれない

事象概要
表題のとおり。
- 手元の作業ブランチコミットをGitHubのリモートリポジトリへpush
- なぜかローカルのgit上では未push扱いになっている
- GitHubリポジトリ側で同ブランチの確認すると対象コミットは反映されている状態
普段はSourceTreeでブランチの管理をしているので、たまに起きるSourceTreeのバグだろうと思ったが、VSCodeのSource Controller上でも同じ扱いとなっていたため、ローカルのgitに何か問題が起きているものと推察。

SourceTreeやgitのロックファイルで何か掴んでるのが残ってたりする可能性を考慮して、各ツールとマシンを再起動をしても状況変わらず。

ブランチ名を改めて確認。同名のブランチのはずだが…そこはかとない既視感を覚える

そういえば1年ほど前、ファイルパスの大文字・小文字問題にハマったことを思い出す。

GitHub上のブランチをよくよく確認すると、同名のブランチが2つ存在していた。
そして片方のブランチ名 feature
の先頭が大文字の Feature
になっていることに気付く。
これじゃん。

issue作成時にブランチとの紐づけを行うため、issueのDevelopmentからブランチを作成。手元へそのブランチをプルして作業する運用にしていたのだが、どうやらブランチ作成時にブランチ名の先頭を大文字の Feature
としてしまっていたようだ。
前述の記事でも言及しているが、gitはデフォルト設定だとパスの大文字/小文字を区別しない設定になっている。
If true, this option enables various workarounds to enable Git to work better on filesystems that are not case sensitive, like FAT. For example, if a directory listing finds "makefile" when Git expects "Makefile", Git will assume it is really the same file, and continue to remember it as "Makefile".
The default is false, except git-clone[1] or git-init[1] will probe and set core.ignoreCase true if appropriate when the repository is created.
手元の環境で設定確認してみると、大文字/小文字の区別を無視するデフォルト設定のままになっていた。
$ git config -l --local | grep core.ignorecase
core.ignorecase=true
前回記事の環境であるMacでは設定変更済みだが、今回作業を行っていたWindows環境ではこの設定変更を適用していなかったようだ。
そのため、GitHubのリモートリポジトリからプルしたブランチ名の feature
が小文字になっていた。
一方、GitHub側ではパスの大文字/小文字の識別がされるため、pushをすると先頭大文字/小文字の異なる同名のブランチが生成されてしまっていた。

少々ややこしいが…
- pushされたブランチは小文字
feature
なので、リモートも同名の小文字ブランチが更新される - リモートの大文字
Feature
ブランチは更新されない - ローカルのgitが参照しているブランチは大文字
Feature
の方なので、更新がないため未push扱いとなっていた

まぁそれはそう、という話だが、パッと見で大文字/小文字の判別ができず、無駄に頭を悩まされてしまった。先頭大文字のブランチは破棄し、小文字ブランチに統合することで無事解決。
同じ轍を踏まぬよう、対象環境でもcore.ignoreCaseの設定変更を施してclose
$ git config core.ignorecase false
$ git config -l --local | grep core.ignorecase
core.ignorecase=false

整理して記事化した

こういうのもあるらしい的な情報メモ