.gitignoreの書き方と仕様を、具体例をまじえてまとめました。「あれ?うまく反映されない・・」など、gitの仕様の理解不足からくるトラブルも解決していきます。
目次
.gitignore の基本
.gitignore とは、Git による追跡から特定のファイルを除外するための設定を書き込むファイルです。
あるGit 管理対象とししているディレクトリでも、その中のすべてのファイルを Git で管理したいとは限りませんので「Git で追跡しないファイル」を .gitignore を使って明示的に指定する事ができます。
.gitignore の仕様をおさらい
まず最初に理解する必要があるのは、.gitignore の仕様です。具体的には、「.gitignore に記載された対象ファイルは、git add の実行時に、インデックスに追加されないようになる」という点だと思います。
言い換えると、.gitignore に記載されたファイルは、記載された時点で「Git の追跡対象から除外される」のではなく「まだ追跡されていないファイルが指定されていれば、git add の実行時にも、追跡を開始しないようになる」という点です。
あとから変更した .gitignore が反映されない?
上記の仕様から、もうすでにgit add されてしまっているファイルは、gitignore に記載に関係なく、追跡が続いてしまうのです。
もしすでに追跡してしまっているファイルを Git の追跡対象から除外したいのであれば、下記のコマンドでインデックスからファイルを削除し、トラッキングを停止することができます。
このコマンドを、.gitignore による除外設定と同時に実行して下しさい。
# インデックスからのみファイルを削除する(追跡対象からはずす) git rm --cached <FILE_NAME>
インデックス領域を示すオプション「--cached」をつけることで、作業ツリーのファイル実体はそのままで、インデックスからのみファイルを削除できます。この --cachedオプションなしで実行すれば「git rm」は作業ツリー上のファイルの実体と、インデックスの両方を削除します。
逆に、もし作業ツリーのファイル実体のみ削除するのであれば、Git でない通常のシェルスクリプト「rm」を使ってファイルを削除することになります。
これらは状況に応じて、使い分ける事になります。
.gitignore の書き方
それでは、.gitignore の正しい書き方をおさらいしましょう。
.gitignoreは、各行に、ファイルをマッチするための「パターン」を記述します。これはshell でのパスの指定方法と「似ているけど少し異なる点がある」ため、注意が必要です。
このパターン記述は git 内で共通の記法となっています。(git add などのときのファイル指定とおなじ)
特定のファイルを追跡対象から除外する
まずは、基本形です。
現状の .gitignore が置かれたディレクトリの直下のファイルか、ディレクトリに関係なくマッチする名前のファイルかどうかは、行頭の「/」の有り無しで使い分けることができます。
すなわち、行頭に「/」があれば、.gitignore が配置されたディレクトリが基準となりますが、ディレクトリ名やファイル名から行頭がはじまれば、ディレクトリに無関係にそのファイルパスをマッチングします。
# どのディレクトリかを問わず、file.phpを除外
file-a.php
# .gitignore が置かれたディレクトリ内のfile.phpを除外
/file-a.php
特定のディレクトリを追跡対象から除外する
ディレクトリ配下のファイルを全て追跡対象から除外するときは、末尾に「/(スラッシュ)」を配置します。
末尾の「/」は特別な意味を持つ、「ディレクトリとその配下の除外」を意味する記号となり、仮に同じ名前のファイルが存在してもマッチング対象にはなりません。
もしスラッシュがなければ、通常のパターンマッチングとなり、パスにマッチがみつかればそれを除外します。
ファイルと同様、開始「/」を付けなければ、ディレクトリに無頓着になります。
# 文字列マッチが見つかるパスを除外する
directory-a
# ディレクトリ配下(のすべてのパスを)除外する
directory-a/
Git でディレクトリを追跡?
Gitではそもそも空っぽのディレクトリ単体は追跡できません。Gitでは、ファイルを管理対象とし、そのファイルのパスとしてディレクトリが記録されるだけだからです。運用上の都合で、ディレクトリを無理やりレポジトリに残すために、そのディレクトリ直下に「.gitignore」を新たに追加してそのファイルを追跡対象に含めたり、または、「.keep」などの名前を付けた空ファイルを配置する慣習があります。(これには賛否ありますが、運用しやすければ。好きなようにすればよいと個人的には思います)ワイルドカードの利用
gitignoreでは、ワイルドカード「*」および「?」が利用できます。
「*」は「/(スラッシュ)以外の文字列」、「?」は、「/(スラッシュ)以外の一文字」にマッチします。
# 「.htaccess」と「.htpasswd」など、.ht で始まるファイルを追跡しない
.ht*
# すべてのファイルを追跡しない
*
また、正規表現でおなじみの「[」「]」を使った文字クラスも利用できます。
# detail-1.html ~ detail-9.html をマッチ
detail-[1-9].html
正規表現の参考記事です。
特定のファイルだけ追跡する
.gitignore では通常は無視するファイルを記載しますが、逆に、特定のファイルだけを追跡対象にふくめたい場合、ワイルドカード「*」と、同時に否定を表す「!」を行頭に置くと、その行の反対、すなわち「ignoreしない」を設定できます。
# file-to-track.phpだけを追跡する。 * !/file-to-trak.php
このように、.gitignore では、後に書いた除外設定が、最初に書いた設定内容を上書きするように動作します。
ただし、一度記述した「ディレクトリの除外」を、跡から!で追跡しなおす設定は認められません。
# 2行目の設定は無効。 /directory/ !/directory/file.html
特定のディレクトリ内のファイルだけを追跡する
上記での触れましたが、ディレクトリ内に何らかのファイルが配置されている事に注意して下さい。Git では空っぽのディレクトリは管理できません。
# directory-a のみを追跡 * !/direcotry-a/
特定の拡張子を無視する
ワイルドカードを利用して、jpgとpngを無視します。どのディレクトリにあるファイルかケアしません。
*.jpg *.png
特定の拡張子を追跡する
簡単な応用ですね。phpだけをトラックします。
!*.php
コメントアウトの書き方
すでになんども例で使っていますが、.gitignoreでは、「#」でコメントアウトできます。
# This is commented out.
エスケープの仕方
これも利用するか不明ですが、特殊文字をエスケープできます。!マークや、スペースをエスケープするのに使う、かもしれません・・。筆者は使ったことはありません。
/\!important.txt
.gitignore のグローバル設定
レポジトリごとに .gitignore を記述するのは手間な場合、~/.config/git/inoreを記述する事で、すべてのレポジトリで設定を有効化することができます。(古いGitバージョンでは、~/.gitignore_global が該当ファイルです)
初期設定は以下のようになっていると思います。
*~
.DS_Store
当然ですが、このグローバル設定はレポジトリで管理できませんので、チームで複数人で開発する時は気をつけましょう。
【応用編】.gitignore による複雑な追跡設定
実際のプロジェクトでは、もうすこし複雑な.gitignoreを書く必要が生じることもあるかもしれません。
例えば、下記は、Wordpress開発で、コアファイルとプラグインなど無視し、テーマと設定ファイルだけをトラックする例です。もう少しキレイに書けるかもしれませんが、理解しやすさを重視して書きます。
追跡するファイル
- /wp-content/themes/my-theme/*
- /wp-config.php
.gitignore の例
ポイントとしては、「末尾スラッシュ」を利用したディレクトリの除外設定を書かないことです。上記で言及しましたが、ディレクトリの除外設定を跡から解除することができませんので、この例のように「*」を使ってディレクトリでなく、パス除外の設定行にする必要があります。
* !/wp-config.php !/wp-content/ /wp-content/* !/wp-content/themes/ /wp-content/themes/* !/wp-content/themes/my-thenme/
【参考】MacOsで.gitginore が反映されない?
Macでどうしてもgitginore が反映されない時、それはおそらく「fileformat」が問題かもしれません、。file format がmac だと、改行コードの問題で、gitignore がうまく読み込まれないことがあります。fileformat の値をunix に変更してあげましょう。
vim .gitignore // 値を確認 :set ff? //結果 mac // 値を変更して終了。 :set ff=unix :wq
参考
.gitignore に関する参考情報
以上になります。いったん理解すれば、難しくはないですね。以下、gitの公式ドキュメントです。
それでは、楽しいgitライフを。