GitGit [ギット]ソースコードの変更履歴を管理する分散型バージョン管理システムで作業中、git statusコマンドを実行して変更されたファイルの一覧は確認できるものの、「具体的にどこをどう変更したんだっけ?」と、ファイルの中身まで把握できずに困った経験はありませんか?特に複数のファイルを修正している場合や、しばらく作業から離れていた場合、どの変更をステージングし、どの変更をコミットするべきか判断に迷うこともあるでしょう。
この記事では、Gitの基本コマンドであるgit statusと、変更内容の差分を表示するgit diffコマンドを組み合わせることで、ワークツリーやステージングエリアの変更内容をスマートに、そして効率的に確認する方法を解説します。この記事を読めば、あなたのGitワークフローがよりスムーズになり、自信を持ってコミットできるようになるでしょう。
確認した環境
この記事は以下の環境で動作確認を行っています。
- OSOS [オーエス]Operating System。基本ソフトウェア: UbuntuUbuntu [ウブントゥ]人気のLinuxディストリビューション 22.04 LTS
- Git: 2.34.1
git statusだけでは分からない変更内容を把握する重要性
Gitを使った開発では、コードの変更履歴を正確に管理することが不可欠です。git statusは現在のリポジトリの状態を把握するための非常に重要なコマンドですが、これだけでは変更されたファイルの中身までは分かりません。変更内容を正確に把握することは、以下のような点で重要です。
- 意図しない変更の発見: 誤って追加・削除してしまったコードや、デバッグ用のコードが残っていないかを確認できます。
- コミットメッセージの精度向上: 変更内容を理解していれば、より具体的で意味のあるコミットメッセージを作成でき、後から履歴を追う際に役立ちます。
- レビューの効率化: 他のメンバーがレビューする際にも、変更者が意図を正確に伝えやすくなります。
- コンフリクトの回避・解決: 変更内容を把握していれば、マージ時のコンフリクトを未然に防いだり、発生した場合にスムーズに解決したりできます。
git statusで確認できる情報の基本おさらい
まずは、git statusコマンドがどのような情報を提供してくれるのか、基本的なおさらいをしましょう。
git statusこのコマンドを実行すると、通常以下のような情報が表示されます。
On branch mainYour branch is up to date with 'origin/main'.
Changes to be committed: (use "git restore --staged <file>..." to unstage) modified: src/index.js
Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: README.md
Untracked files: (use "git add <file>..." to include in what will be committed) new_feature.txtOn branch main: 現在作業しているブランチ名が表示されます。Your branch is up to date with 'origin/main'.: リモート追跡ブランチ(upstream)が設定されている場合、ローカルブランチとローカルに記録されているリモート追跡ブランチとの比較結果が表示されます。なお、リモートリポジトリの最新状態を反映するには、事前にgit fetchを実行する必要があります。Changes to be committed:: ステージングエリアに追加され、次のコミットに含まれる変更です。この例ではsrc/index.jsが変更されています。Changes not staged for commit:: ワークツリー(作業ディレクトリ)で変更されたものの、まだステージングエリアに追加されていない変更です。この例ではREADME.mdが変更されています。Untracked files:: Gitの追跡対象になっていないファイルです。新しく作成したファイルのほか、git rm --cachedなどで追跡対象から外されたファイルなども該当します(この例ではnew_feature.txt)。
git statusはデフォルトではファイルの「状態」のみを教えてくれますが、具体的に「何がどう変わったのか」までは表示されません。
変更されたファイルの中身(差分)まで一目で見る方法
git statusの実行時に変更内容(差分)までまとめて確認したい場合は、-v(または --verbose)オプションを指定する方法があります。
# ステージング済みの差分もあわせて表示するgit status -v
# ステージング済み・未ステージ両方の差分をすべて表示するgit status -vvgit status -v: 通常のステータス表示の下に、ステージングエリアに追加された変更の差分(後述するgit diff --cached相当)を表示します。git status -vv:-vを2つ重ねると、ステージング済みの差分に加えて、まだステージングしていないワークツリーの変更の差分(git diff相当)も一括で表示します。
なお、git status -v / -vv で差分が表示されるのは、Gitが追跡しているファイルの変更内容です。Untracked files についてはファイル名は表示されますが、ファイルの中身は差分として表示されません。
手軽に全体の差分をざっと眺めたいときには git status -v / -vv が便利ですが、変更ファイルが多い場合や、ステージング前後・特定のファイルだけを切り分けて確認したい場合には、差分表示専用の git diff コマンドを組み合わせるのが効率的です。ここからは、git diff を使った実践的な確認方法を詳しく見ていきましょう。
ステージング前後の差分を効率よく確認するコマンド
Gitのワークフローでは、変更をステージングする前と後で、それぞれ異なる差分を確認することが重要です。これにより、意図しない変更がコミットされるのを防ぎます。
git diffでワークツリーとステージングエリアの差分を見る
最も基本的なgit diffコマンドは、ワークツリー(作業ディレクトリ)の変更と、ステージングエリアの変更との差分を表示します。これは、まだgit addしていない変更の内容を確認したい場合に利用します。
git diff例えば、README.mdファイルを修正したが、まだgit add README.mdを実行していない状態でこのコマンドを実行すると、以下のような出力が得られます。
diff --git a/README.md b/README.mdindex 724a87c..1d6704a 100644--- a/README.md+++ b/README.md@@ -1,3 +1,4 @@ # My Awesome Project
This is a sample project.+A new line has been added here.出力の読み方:
diff --git a/README.md b/README.md:aとbは比較対象のファイルを示します。index 724a87c..1d6704a 100644: Git内部のオブジェクトIDとファイルモードを示します。--- a/README.md: 比較元のファイル(ステージングエリアに記録されている変更前の状態)を示します。+++ b/README.md: 比較先のファイル(ワークツリーの現在の状態)を示します。@@ -1,3 +1,4 @@: 差分が表示されている行の位置と行数を示します。-1,3は「比較元の1行目から始まる3行分」、+1,4は「比較先の1行目から始まる4行分」を表します。- 行の先頭の記号:
(スペース): 変更がない行+: 新しく追加された行-: 削除された行
このコマンドは、あなたが作業ディレクトリで行った変更が、ステージングエリアにある内容とどのように異なるかを示します。これにより、「この変更をgit addして良いか?」を判断できます。
なお、git diff で表示されるのはGitが追跡しているファイルの差分のみであり、Untracked files(未追跡ファイル)の内容は表示されません。新規作成したファイルの差分を確認したい場合は、git add -N <ファイル名>(--intent-to-add)でインデックスに「追加予定(Intent-to-add)」として登録してから git diff を実行する方法があります。ただし、git add -N は通常のステージングとは異なり、ファイルの内容そのものをインデックスに登録する操作ではありません。通常の git commit で新規ファイルの内容をコミット対象に含める場合は、改めて git add <ファイル名> を実行してください。
--cachedオプションでコミット前の差分を確認する
git addコマンドで変更をステージングエリアに追加した後、実際にコミットする前にその内容を最終確認したい場合があります。このようなときに使用するのがgit diff --cached(またはgit diff --staged)コマンドです。
このコマンドは、ステージングエリアの内容と、最新のコミット(HEAD)との差分を表示します。
git diff --cached# またはgit diff --staged例えば、src/index.jsファイルを修正し、git add src/index.jsを実行した後にこのコマンドを実行すると、以下のような出力が得られます。
diff --git a/src/index.js b/src/index.jsindex f123abc..d456def 100644--- a/src/index.js+++ b/src/index.js@@ -1,6 +1,7 @@ console.log("Hello, Git!");
function greet(name) {- console.log(`Hello, ${name}!`);+ console.log(`Greetings, ${name}!`); // Changed greeting message }+ greet("World");この出力は、あなたがステージングエリアに追加した変更が、前回のコミットからどのように変わったのかを示します。これにより、「この内容でコミットして良いか?」を最終的に判断できます。意図しない変更が含まれていれば、git restore --staged <ファイル名>でステージングを解除し、再度修正することができます。
補足:git diff HEADでステージング前後をまとめて確認する
ステージング済みの変更と未ステージの変更を区別せず、最新のコミット(HEAD)と現在のワークツリーとの差分をまとめて確認したい場合は、git diff HEAD を使用します(※この場合も Untracked files の内容は表示されません)。
git diff HEADここまで紹介した3つの git diff コマンドの比較対象を整理すると、以下のようになります。
| コマンド | 比較対象 | 主な用途 |
|---|---|---|
git diff | インデックス(ステージング) ↔ ワークツリー | git add する前の未ステージ変更を確認する |
git diff --cached (--staged) | HEAD(最新コミット) ↔ インデックス | git commit する前のステージング済み変更を確認する |
git diff HEAD | HEAD(最新コミット) ↔ ワークツリー | ステージング前後を問わず、追跡対象ファイルの最新コミットからの変更を確認する |
特定のファイルだけピンポイントで変更内容を確認するコツ
プロジェクトが大きくなると、一度に複数のファイルを変更することがよくあります。その中で、特定のファイルだけに着目して変更内容を確認したい場合もあるでしょう。git diffコマンドにファイル名を指定することで、これを実現できます。
# ワークツリーとステージングエリア間の特定のファイルの差分git diff <ファイル名>
# ステージングエリアと最新コミット間の特定のファイルの差分git diff --cached <ファイル名>例えば、README.mdの変更だけを確認したい場合は、以下のように実行します。
git diff README.mdステージング済みのsrc/index.jsの変更だけを確認したい場合は、以下のように実行します。
git diff --cached src/index.js複数のファイルを指定することも可能です。
git diff file1.txt file2.txtgit diff --cached file3.js file4.cssこのテクニックは、特に大規模な変更セットの中から特定の変更をレビューしたい場合や、特定のファイルに問題がないかを確認したい場合に非常に役立ちます。
実務で役立つ!git statusとdiffの組み合わせテクニック
実際の開発現場では、git statusとgit diffを組み合わせて使うことで、より効率的なワークフローを構築できます。
1. 変更の全体像を把握し、個別の差分を確認する
-
git statusで全体像を把握: まずgit statusを実行して、どのファイルが変更され、どの状態にあるか(Untracked, Not Staged, Staged)を一覧で確認します。Terminal window git status -
git diffで未ステージの変更を確認:Changes not staged for commitセクションに表示されたファイルについて、git diff <ファイル名>を実行して、ワークツリーでの変更内容を確認します。これにより、変更をステージングして良いか判断します。Terminal window git diff README.mdgit diff src/utils.js -
git addで変更をステージング: 確認した変更が意図通りであれば、git add <ファイル名>でステージングします。Terminal window git add README.md -
git diff --cachedでステージング後の最終確認:git addした後に、git diff --cached <ファイル名>を実行して、ステージングエリアの内容がコミットされる内容として適切か最終確認します。Terminal window git diff --cached README.mdまたは、ステージングエリア全体の変更を確認するために、ファイル名を指定せずに
git diff --cachedを実行します。Terminal window git diff --cached
このフローを繰り返すことで、意図しない変更がコミットされるリスクを最小限に抑えられます。
2. git status -s (ショートフォーマット) との組み合わせ
git status -s (または --short) は、git statusの出力を簡潔な形式で表示します。これは、多数のファイルが変更されている場合に、一覧性を高めるのに便利です。
git status -s出力例:
M README.mdM src/index.js?? new_feature.txt先頭の2文字のステータスコード(XY)は、1文字目(X:左列)がステージングエリアの状態、2文字目(Y:右列)がワークツリーの状態を表しています。空白の位置によって意味が異なるため、以下の表とあわせて確認すると分かりやすくなります(␣ は半角スペースを表します)。
| 表示(1文字目・2文字目) | 状態の意味 |
|---|---|
␣M(1文字目が空白、2文字目がM) | ワークツリーで変更あり(未ステージ) |
M␣(1文字目がM、2文字目が空白) | ステージング済み(その後のワークツリー変更なし) |
MM | ステージング後にワークツリーでもさらに変更あり |
AM | 新規ファイルをステージングした後、さらにワークツリーで変更あり |
?? | Untracked files(Gitの追跡対象になっていないファイル) |
上記の出力例に当てはめると、それぞれのファイルは以下の状態であることが一目で分かります。
M README.md: 1文字目が空白、2文字目がMのため、ワークツリーで変更された未ステージのファイルです。M src/index.js: 1文字目がM、2文字目が空白のため、変更がステージング済みで、その後ワークツリーでは変更されていないファイルです。?? new_feature.txt: Gitの追跡対象になっていない(Untracked)ファイルです。
このショートフォーマットで変更されたファイルと状態(未ステージかステージング済みか)を特定し、それに応じたgit diffコマンドを実行することで、効率的に差分を確認できます。
# 未ステージの変更を確認git diff README.md
# ステージング済みの変更を確認git diff --cached src/index.js3. 変更を破棄する前の最終確認
もし、ワークツリーの変更を破棄したい場合(例: git restore <ファイル名>やgit checkout -- <ファイル名>を実行する前)、本当にその変更を捨ててしまって良いか不安になることがあります。そんな時もgit diffが役立ちます。
# ワークツリーの変更を破棄する前に内容を確認git diff <ファイル名>このコマンドで変更内容を確認し、問題ないことを確認してからgit restore <ファイル名>を実行すれば、誤って必要な変更を破棄してしまうリスクを減らせます。
トラブルシューティング: git diffで何も表示されない場合
- 変更がステージングされている可能性:
git diffはワークツリーとステージングエリアの差分を表示します。もし変更がすでにgit addされている場合は、git diff --cached(またはステージング前後をまとめて確認できるgit diff HEAD)で確認してください。 - Untracked files(未追跡ファイル)である可能性: 新規作成したばかりのファイルなど、Gitの追跡対象になっていないファイルは
git diffでは表示されません。必要に応じてgit add -N <ファイル名>を実行してからgit diffで確認してください。 - 変更がコミットされている可能性: 変更がすでに
git commitされている場合、git diffもgit diff --cachedも何も表示しません。その場合は、git logでコミット履歴を確認するか、git show <コミットハッシュ>で特定のコミットの変更内容を確認します。 - ファイル名が間違っている可能性: 指定したファイル名が間違っていると、差分は表示されません。
git statusで正確なファイル名を確認してください。
まとめ
この記事では、git statusとgit diffを組み合わせて、Gitリポジトリの変更内容を効率的に確認する方法を解説しました。
git statusは、ファイルの「状態」(Untracked, Not Staged, Staged)を把握するのに役立ちます。-v(ステージング済みの差分表示)や-vv(未ステージを含む全差分表示)オプションを使えば、ステータスと同時に差分を確認することも可能です。git diffは、ワークツリーとステージングエリア間の差分を表示し、まだgit addしていない変更内容を確認する際に使用します。git diff --cachedは、ステージングエリアと最新コミット間の差分を表示し、コミット前にステージング済みの変更内容を最終確認する際に使用します(ステージング前後をまとめて最新コミットと比較したい場合はgit diff HEADが便利です)。git diff <ファイル名>のようにファイル名を指定することで、特定のファイルのみの差分をピンポイントで確認できます。git status -s(ショートフォーマット)とgit diffを組み合わせることで、多数の変更がある場合でも効率的に差分を確認し、コミット準備を進めることができます。- 変更を破棄する前に
git diffで最終確認を行うことで、意図しないデータ損失を防ぐことが可能です。
これらのコマンドとテクニックを習得することで、あなたのGitワークフローはよりスムーズになり、自信を持って変更を管理できるようになるでしょう。
以上で本記事の解説を終わります。
よいITライフを!
人気記事
- 1
- 2
- 3
- 4
- 5
とにかく挫折しない丁寧な解説。チーム開発での基本的な流れを確実にマスターできます。