在本节中,我们将重点详细讨论 git clean 命令。Git clean 在某种程度上是一个“撤销”命令。Git clean 可以被视为是 git reset git checkout 等其他命令的补充。其他命令对先前添加到 Git 跟踪索引的文件进行操作,而 git clean 命令则对未跟踪文件进行操作。未跟踪文件是在代码存储库的工作目录中创建但尚未使用 git add 命令添加到存储库跟踪索引的文件。为了更好地演示跟踪文件和未跟踪文件之间的区别,请考虑以下命令行示例

$ mkdir git_clean_test
$ cd git_clean_test/
$ git init .
Initialized empty Git repository in /Users/kev/code/git_clean_test/.git/
$ echo "tracked" > ./tracked_file
$ git add ./tracked_file
$ echo "untracked" > ./untracked_file
$ mkdir ./untracked_dir && touch ./untracked_dir/file
$ git status
On branch master

Initial commit

Changes to be committed: (use "git rm --cached <file>..." to unstage)

new file: tracked_file

Untracked files: (use "git add <file>..." to include in what will be committed) untracked_dir/ untracked_file

该示例在 git_clean_test 目录中创建了一个新的 Git 存储库。然后,它继续创建一个 tracked_file 并将其添加到 Git 索引中,此外,还会创建一个 untracked_fileuntracked_dir。然后,该示例调用 git status,显示指示 Git 跟踪和未跟踪变更的内部状态的输出。当存储库处于这种状态时,我们可以执行 git clean 命令来演示其预期用途。

$ git clean fatal: clean.requireForce defaults to true and neither -i, -n, nor -f given; refusing to clean

此时,执行默认的 git clean 命令可能会产生致命错误。上方示例演示了这可能是什么样子。默认情况下,Git 是全局配置的,要求向 git clean 传递“强制”选项才能启动。这是一个重要的安全机制。最终执行时,git clean 是不可撤销的。完全执行后,git clean 将执行硬文件系统删除,类似于执行命令行 rm 实用程序。请确保您真的要删除未跟踪文件,之后再运行该命令。

常用选项和用法

根据前面对 git clean 默认行为的解释和注意事项,以下内容演示了各种 git clean 用例及其操作所需的随附命令行选项。

-n

-n 选项将执行 git clean 的“试运行”。这将显示哪些文件将在不实际删除的情况下被删除。最佳实践是始终先执行 git clean 的试运行。我们可以在之前创建的演示代码存储库中演示此选项。

$ git clean -n
Would remove untracked_file

输出告诉我们,执行 git clean 命令时,untracked_file 将被删除。请注意,此处的输出中未报告 untracked_dir。默认情况下,git clean 不会对目录进行递归操作。这是防止意外永久删除的另一种安全机制。

-f or --force

强制选项启动从当前目录中实际删除未跟踪文件。除非 clean.requireForce 配置选项设置为 false,否则需要强制进行。这不会删除 .gitignore 指定的未跟踪文件夹或文件。现在我们在示例代码存储库中执行实时的 git clean 操作。

$ git clean -f 
Removing untracked_file

该命令将输出已删除的文件。您可以在这里看到 untracked_file 已被删除。此时执行 git status 或执行 ls 会显示 untracked_file 已被删除,无处可寻。默认情况下,git clean -f 将针对所有当前目录未跟踪文件进行操作。此外,可以使用 -f 选项传递 < path > 值,该选项将删除特定的文件。

git clean -f <path>
-d include directories

-d 选项告诉 git clean 您还想删除所有未跟踪目录,默认它会忽略目录。我们可以在之前的示例中添加 -d 选项:

$ git clean -dn
Would remove untracked_dir/
$ git clean -df
Removing untracked_dir/

这里我们使用 -dn 组合执行了“试运行”,其输出 untracked_dir 有待删除。然后我们执行强制清理,并收到删除 untracked_dir 的输出。

-x force removal of ignored files

常见的软件发布模式是创建一个不提交到存储库跟踪索引的版本或分发目录。版本目录将包含由提交的源代码生成的临时版本构件。这个版本目录通常会添加到存储库 .gitignore 文件中。使用其他未跟踪文件清理此目录也可能很方便。-x 选项告诉 git clean 还包括所有被忽略的文件。与之前的 git clean 调用一样,最佳实践是在最后一次删除之前先执行“试运行”。-x 选项将作用于所有被忽略的文件,而不仅仅是特定于项目版本的文件。这可能是意想不到的文件,比如 ./.idea IDE 配置文件。

git clean -xf

像 -d 选项一样,-x 可以传递并与其他选项合成。此示例演示了与 -f 的组合,它将从当前目录中删除未跟踪文件以及 Git 通常会忽略的任何文件。

交互模式或 git clean 交互

除了我们到目前为止演示的临时命令行执行外,git clean 还具有“交互”模式,您可以通过传递 -i 选项来启动该模式。我们重温一下本文档介绍中的示例代码存储库。在初始状态下,我们将启动交互式清理会话。

$ git clean -di
Would remove the following items:
  untracked_dir/  untracked_file
*** Commands ***
    1: clean                2: filter by pattern    3: select by numbers    4: ask each             5: quit                 6: help
What now>

我们已经使用 -d 选项启动了交互式会话,因此它也会对我们的 untracked_dir 起作用。交互模式将显示 What now> 提示符,该提示符请求将命令应用于未跟踪文件。这些命令本身是不言自明的。我们将从命令 6: help 开始,按随机顺序简要介绍每个命令。选择命令 6 将进一步解释其他命令:

What now> 6
clean               - start cleaning
filter by pattern   - exclude items from deletion
select by numbers   - select items to be deleted by numbers
ask each            - confirm each deletion (like "rm -i")
quit                - stop cleaning
help                - this screen
?                   - help for prompt selection
5: quit

直截了当,并将退出交互式会话。

1: clean

将删除指定的项目。如果我们现在要执行 1: cleanuntracked_dir/ untracked_file 将被删除

4: ask each

将遍历每个未跟踪文件并针对删除显示 Y/N 提示符。它看起来如下所示:

*** Commands ***
    1: clean                2: filter by pattern    3: select by numbers    4: ask each             5: quit                 6: help
What now> 4
Remove untracked_dir/ [y/N]? N
Remove untracked_file [y/N]? N
2: filter by pattern

将显示一个额外的提示,该提示接受用于筛选未跟踪文件列表的输入。

Would remove the following items:
  untracked_dir/  untracked_file
*** Commands ***
    1: clean                2: filter by pattern    3: select by numbers    4: ask each             5: quit                 6: help
What now> 2
  untracked_dir/  untracked_file
Input ignore patterns>> *_file
  untracked_dir/

在这里,我们输入 *_file 通配符模式,然后将未跟踪文件列表限制为 untracked_dir

3: select by numbers

与命令 2 类似,命令 3 用于优化未跟踪文件名的列表。交互式会话将提示输入与未跟踪文件名相对应的数字。

Would remove the following items:
  untracked_dir/  untracked_file
*** Commands ***
    1: clean                2: filter by pattern    3: select by numbers    4: ask each             5: quit                 6: help
What now> 3
    1: untracked_dir/    2: untracked_file
Select items to delete>> 2
    1: untracked_dir/  * 2: untracked_file
Select items to delete>>
Would remove the following item:
  untracked_file
*** Commands ***
    1: clean                2: filter by pattern    3: select by numbers    4: ask each             5: quit                 6: help

摘要

总而言之,git clean 是一种删除代码存储库工作目录中未跟踪文件的便捷方法。未跟踪文件是指存储在代码存储库目录中,但尚未使用 git add 添加到代码存储库索引中的文件。总体而言,git clean 的效果可以使用 git status 和操作系统的本机删除工具来实现。Git clean 可以与 git reset 一起使用,以完全撤销存储库中的任何添加和提交。