🔠

Gitで大小文字の差分が反映されない理由と確実な直し方

に公開

理由

  • macOS の標準設定ではパス(ファイル/フォルダ)の大小文字違いを同一扱いする
  • リモートに大小文字違いが共存すると、ローカルに同時に展開できず混ざる
  • その結果、差分が見えない・操作が意図どおりにならない

直し方

  • git config core.ignorecase false にして大小文字の違いが見える状態にする
  • git status で差分や未追跡を確認する
  • git add して git commit する

APFS と大小文字

macOS 標準のファイルシステムにはAPFSが利用されています。
多くの macOS は APFS の大小文字を区別しない設定で使われており、この場合 StoryBookStorybook は同一扱いになります。

症状

GitHub 上ではスクリーンショットのように、StoryBookStorybook が別フォルダとして共存できます。
筆者の環境では、誤って一部のファイルのみ変更した場合に気付かないうちにフォルダが出来上がってしまいました。
ここが落とし穴で、GitHub は大小文字を区別できるため、リポジトリのツリーとしては「両方が存在する」状態が成立してしまいます。

StorybookとStoryBookが混在したGitHubのスクリーンショット

一方で macOS の標準設定では大小文字違いを同一扱いするため、ローカルでは StoryBookStorybook を同じ場所(Storybook)として扱ってしまいます。
なので下記のようにStoryBookフォルダはStorybookとして扱われます。

$ ls -al

drwxr-xr-x   5 user  staff 他のファイル
drwxr-xr-x   5 user  staff Storybook

Finder では 1 つのフォルダに見えるのに、実際はブランチや履歴の状態によって中身が混ざり、環境が汚染されたような状態になります。

この状態だと git status で期待した差分が見えなかったり、大小文字だけの変更が反映されません。

対応方法

確認

まずはcore.ignorecase を確認しましょう。

git config --get core.ignorecase

上記コマンドの出力結果は下記のように解釈します。

  • true: Gitはパス(ファイル/フォルダ名)の大小文字違いを同一視します
  • false: Gitは大小文字違いを別物として扱います(case-sensitive寄り)

結果がtrueの場合、解決方法は簡単です。

解決

git config core.ignorecase false を実行し差分をコミットしましょう。

core.ignorecase の注意点

core.ignorecase は Git がパスの大小文字をどう扱うかに影響します。
macOS の標準設定では true になっていることが多く、この場合は大小文字だけの違いが git status などに出ず、差分として見えません。

自分の環境で git config core.ignorecase false に切り替えたところ、これまで見えていなかった未追跡ファイルが git status に出るようになり、git addgit commit ができました。
この挙動は、Git が StoryBookStorybook を別物として扱うようになり、作業ツリー内の実体との差が表面化するためです。

プロジェクトごとの設定が面倒ならgit config --global core.ignorecase false でグローバル設定も可能です。

まとめ

  • リモートに大小文字違いが共存すると、macOS では衝突してローカルが壊れる
  • 差分が見えないときは git config core.ignorecase false にして git status を確認すると作業が進むことがある

Discussion