There was a file demo.py
in the git repo, it was deleted in one commit, now for some reason, we need to restore it.
- Locate which commit deleted the file
git log --full-history --oneline demo.py
The output will list a lot of commits, which changes the file demo.py
.
Locate the commit id, for instance, 66a0808
deleted the file.
- Restore the file
git checkout 66a0808^ -- demo.py
Or use git restore
to recover the file, since this command fits our expectation better(Although them do the same thing):
git restore --source 66a0808^ -- demo.py
Pay attention to the ^
.
- Make a commit
git status
# new file: demo.py
git add -u
git commit -m "Restore file demo.py"
A better method to locate the commit which deleted a specific file
git log --oneline --all --stat --diff-filter=D | grep "demo.py"
# List the commits which deleted the file "demo.py"
Reference: https://git-scm.com/docs/git-log
--diff-filter=[(A|C|D|M|R|T|U|X|B)…[*]]
Select only files that are Added (A), Copied (C), Deleted (D), Modified (M), Renamed (R), have their type (i.e. regular file, symlink, submodule, …) changed (T), are Unmerged (U), are Unknown (X), or have had their pairing Broken (B). Any combination of the filter characters (including none) can be used. When * (All-or-none) is added to the combination, all paths are selected if there is any file that matches other criteria in the comparison; if there is no file that matches other criteria, nothing is selected.Also, these upper-case letters can be downcased to exclude. E.g. --diff-filter=ad excludes added and deleted paths.
Note that not all diffs can feature all types. For instance, diffs from the index to the working tree can never have Added entries (because the set of paths included in the diff is limited by what is in the index). Similarly, copied and renamed entries cannot appear if detection for those types is disabled.
An alternative way to restore the file:
For instance, the commit "aec723390" deleted the file "test.log":
git restore --source aec723390^ -- test.log
Reference: https://git-scm.com/docs/git-restore
The following sequence switches to the master branch, reverts the Makefile to two revisions back, deletes hello.c by mistake, and gets it back from the index.
$ git switch master
$ git restore --source master~2 Makefile (1)
$ rm -f hello.c
$ git restore hello.c