【Git】コミット前の変更や修正作業を削除する方法。git checkout .(ドット)の意味と使い方を実例で解説|git reset –hardで削除できないファイルの消し方

git-prograshi(プロぐらし)-kv git/github
記事内に広告が含まれていることがあります。

コードの履歴管理ツールGitを使っていると、ファイルを編集したけど、その内容を全て削除したい、git addしてステージングしたけど、コミットはせずに全ての変更内容をなかったことにしたい(直近のコミットの状態に戻したい)ということがあります。

ここでは、そんな、コミット前の作業を削除する方法についてまとめています。

git checkout .(ドット)がどんな処理をしているかについても解説しています。


ファイルの変更・修正内容を削除する方法

修正を加えたファイルの変更や修正内容を削除して、直近のコミットの状態に戻す方法は、どのファイルを戻すかによって、主に次の2つがあります。

ファイルの変更・修正内容を削除する方法
  1. git addしたファイルも全て元に戻す。
  2. git addする前の変更を全て元に戻す。


git addしたファイルも全て元に戻す

git addしたファイルも全て元に戻すには以下のコマンドを実行します。

git reset --hard HEAD

git resetは指定したコミットに戻るためのコマンドです。

オプションに「–hard」をつけることで変更内容を全て削除することができます。

戻りたいコミットで現在のブランチが指している最新のコミットを表す「HEAD」を指定することで、直近のコミットの状態に戻すことができます。

なお、「HEAD」を「@」にしても同じ処理になります。

git reset --hard @
合わせて読みたい

git resetはGitの中でも多用するとても便利なコマンドです。「–hard」以外にもオプションが用意されており、指定したオプションによって処理の内容が変わります。詳細は下記をご参考ください。

【Git】git reset(リセット)とは何か?使い方を実例で解説|オプションなし、soft, hard, mixedの違い


git addする前の変更を全て元に戻す

git addしたものはそのままで、git addする前の変更を全て元に戻したい場合は「git checkout」を使います。

git checkout .

これで、git add前のすべてのファイルを直近のコミットの状態にするコマンドです。

以下で「git checkout .」の詳細について解説しています。


補足

git reset --hard HEADや、git checkout .を行ったときに、エディタで開いているファイルの内容は編集中の状態で残ることがあります。

その時はファイルを閉じると「変更を保存しますか?」と聞かれるので、「保存しない」とすれば、最新のコミットの状態に戻ります。


git checkout . (ドット)の意味は何か?

git checkoutは何をしているか?

git checkoutはブランチ名を指定して、ブランチを切り替えるときに使うのが一般的です。

このためgit checkoutはブランチを指定したり切り替えるコマンドだと思っている人がいますが、本質的には違います。

git checkout ブランチ名としたとき、裏側で行われている処理は、指定したブランチが指しているコミットに移動するという処理です。

すなわちコミットを指定しているということです。


特定のファイルのみ、指定したコミットの状態に戻す

git checkoutは指定したコミットに移動する処理であるため、移動したいコミットとファイルパスを指定することで、指定したファイルのみ、指定したコミットの状態に戻すことができます

$ git checkout <コミット> <ファイル or ディレクトリパス>

なお、ファイルパスは相対パスで記述でき、ワイルドカード「*」も使えます。

また、ファイルではなくディレクトリを指定することもできます。ディレクトリを指定した場合は、そのディレクトリ配下のファイルが全て、指定したコミットの状態に戻ります。


実例:ファイルを指定

$ git checkout f7325fc test.txt
Updated 1 path from the index


実例:ワイルドカードを使って指定

「st.tx」という文字列を含むすべてのディレクトリやファイルを対象にしたい場合は以下のようにします。

$ git checkout f7325fc *st.tx*
Updated 1 path from 024ecc9


コミットを指定しない場合

git checkoutではコミットを指定せずに、ファイルパスやディレクトリパスだけを指定する記述もあります。

その場合、コミットは最新のコミットを指しているのと同じになります。

$ git checkout <ファイル or ディレクトリパス>

この使い方で、現在のディレクトリを指す「.」を指定すると、現在のディレクトリにある全てのファイルが、直近のコミットの状態に戻ります

$ git checkout .

このため、「git checkout .」とすることで、コミット前の編集した内容を全て削除することができます。

「git checkout .」の実例

例えば、以下のようにgit add済みのファイル「resources/views/index.blade.php」と、ステージ前の変更を加えたファイル「app/Http/Controllers/UserController.php」があるとします。

$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   resources/views/index.blade.php

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:   app/Http/Controllers/UserController.php

この状態で「git checkout .」します。

$ git checkout .
Updated 1 path from the index

再度git statusで状態を確認します。

$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   resources/views/index.blade.php

git add 前の「app/Http/Controllers/UserController.php」の変更内容が消えて、git add後の「resources/views/index.blade.php」のみになったことがわかります。


git checkout .やgit reset –hardでUntracked filesは消せない

Untracked filesは消せない

新規作成でgit addも何もしていないファイルはGitが未追跡なので、git checkout .git reset --hard HEADで戻すことができません。

「git status」で確認すると「Untracked files」(未追跡ファイル)と表示されるファイルです。


実例

例えば以下のように、ステージング済みのファイル「text.txt」と未追跡のファイル「app/assets/stylesheets/articles.scss」があるとします。

#状態確認
$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   test.txt

Untracked files:
  (use "git add <file>..." to include in what will be committed)
        app/assets/stylesheets/articles.scss

このファイルに、「git reset –hard @」を実行して、全ての変更を削除します。

$ git reset --hard @
HEAD is now at 9aa0fb6 [A]test.txt3

再度、git statusをして状態を確認します。

$ git status
On branch master
Untracked files:
  (use "git add <file>..." to include in what will be committed)
        app/assets/stylesheets/articles.scss

nothing added to commit but untracked files present (use "git add" to track)

git addしたファイルは削除されていることがわかりますが、「Untracked files」がそのまま残っています。



未追跡ファイル(Untracked files)を削除する方法

未追跡ファイルは、git cleanで削除することができます。

未追跡のファイルを削除する方法

$ git clean -f


未追跡のディレクトリを削除する方法

$ git clean -df
point

git cleanの対象となるのは未追跡のファイルやディレクトリのみです。既に追跡済みで変更を加えたファイルやgit addしたファイルには影響を及ぼしません。


実例(未追跡ファイルやディレクトリの削除)

例えば以下のように「Untracked files」に複数のファイルとディレクトリがあるとします。

$ git status
On branch master
Untracked files:
  (use "git add <file>..." to include in what will be committed)
        app/assets/stylesheets/articles2.scss
        app/assets/stylesheets/test.scss
        app/views/articles2/
        app/views/test/

nothing added to commit but untracked files present (use "git add" to track)

この状態で「git clean -f」を実行します。

$ git clean -f
Removing app/assets/stylesheets/articles2.scss
Removing app/assets/stylesheets/test.scss

すると、未追跡のファイルだけ削除されたことがわかります。

未追跡のディレクトリはそのまま残っている状態です。

$ git status
On branch master
Untracked files:
  (use "git add <file>..." to include in what will be committed)
        app/views/articles2/
        app/views/test/

nothing added to commit but untracked files present (use "git add" to track)

未追跡のディレクトリを削除するためには、git cleanコマンドで「-df」オプションを実行します。

$ git clean -df
Removing app/views/articles2/
Removing app/views/test/

すると、ディレクトリも削除できました。

git statusで確認すると完全にクリーンになっていることがわかります。

$ git status
On branch master
nothing to commit, working tree clean
タイトルとURLをコピーしました