ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

掌握 `git add`:从暂存区原理到提交历史的精准塑造——GitHub Training Kit 实战指南

掌握 `git add`:从暂存区原理到提交历史的精准塑造——GitHub Training Kit 实战指南
  • 文档
  • 教程

【免费下载链接】training-kit

Open source courseware for Git and GitHub

项目地址:https://gitcode.com/gh_mirrors/tr/training-kit
点击查看免费下载

git add是将工作区改动送入 Git 暂存区(Staging Area / Index)的核心命令,也是每次git commit得以生效的前提。本指南以 GitHub Training Kit 开源课程中的 git-add.md 为主体,结合仓库内的 git-commit.md、git-status.md、git-init.md 与多语言 Git 速查表 等配套材料,系统讲解git add的用途、常用选项、完整工作流示例与撤销方法,帮助你学会用暂存操作把混乱的改动整理成逻辑清晰、便于回溯的提交历史。

一、git add是什么:连接工作区与提交的必经之路

git add命令负责把工作目录中新增或修改的文件添加到 Git 的暂存区(staging area)。它是 Git 工作流里最基础也最关键的环节之一——没有git add,git commit将无任何内容可提交。

git add README.md

在一些开发者看来,git add似乎是开发流程中"多余的一步"。但事实上,它是一个重要且强大的工具:git add允许你在不改变日常工作方式的前提下,主动塑造历史。

Git 的日常修改流程包含三个区域:

区域说明对应命令
工作区(Working Directory)你编辑文件的地方,改动尚未被 Git 记录直接编辑、保存文件
暂存区(Staging Area / Index)存放被选中、准备进入下次提交的快照git add
提交历史(History / Repository)通过提交永久保存的快照序列git commit

仓库内的 git-commit.md 对这两个阶段有明确说明:"提交(Commits)有两个阶段,以帮助你正确地构建提交"——先用git add <FILENAME>指定要"暂存"的文件,再执行git commit;如果不先git add任何文件,git commit命令根本无法工作,因为Git 只从暂存区读取要提交的内容。

什么时候使用git add?

git add README.md

随着工作推进,你会修改并保存一个或多个文件。在提交之前,必须先执行git add。这一步让你能够选择将要提交的内容。理想情况下,提交应该是逻辑上完整、原子化的变更单元——但并非所有人的工作方式都能如此。当你的改动本身并非逻辑或原子化的变更单元时,git add依然允许你有条不紊地塑造你的提交和历史。

git add到底做了什么?

git add [filename]选中该文件,并将其移入暂存区,标记为包含在下一个提交中。你可以选择:

  • 全部文件
  • 一个目录
  • 特定文件
  • 甚至某个文件中的特定片段(通过git add -p)

一个容易混淆的点是:如果你对已删除的文件执行git add,暂存的其实是删除操作。"add"(添加)一词与实际发生的"delete"(删除)语义相反。如果把git add理解为git stage,那么实际发生的事情就会清晰得多。

git add与git commit是相辅相成的——它们脱离彼此都无法正常工作,只有把二者当作一个联合功能来思考时,它们才能发挥出最大价值。

二、git add的常用用法与选项

常用形式

命令作用
git add <path>暂存指定的目录或文件
git add -A暂存整个仓库中所有未被.gitignore排除的文件
git add -p交互式地暂存变更的各个代码块(hunks)

git add -p(即--patch)的实战价值尤其突出。仓库中的 git-commit.md 特意提到:"你也可以使用一个便捷的命令git add -p,来逐一浏览变更并把它们拆分开,即使这些变更位于同一个文件里。"这意味着你可以把同一个文件中属于不同逻辑主题的改动,拆分进不同的提交,这正是"用暂存塑造历史"的精髓。

常用选项速览

  • git add --interactive(-i):进入交互式暂存界面,可逐文件、逐块选择
  • git add --update(-u):仅暂存已跟踪文件中被修改与被删除的部分,不包含新文件
  • git add --all(-A):暂存全部新增、修改与删除
  • git add --dry-run:仅预览将被暂存的内容而不实际执行
  • git add --verbose:输出每个被暂存的文件名

更多完整选项可参考仓库内的多语言 Git 速查表(含简体中文版 zh_CN 速查表),其中将git add [file]定义为"将文件进行快照处理用于版本控制"。

三、完整工作流示例:git add在分支开发中的位置

git add通常嵌入以下标准工作流:

  1. 创建分支:git branch update-readme
  2. 切换到该分支:git checkout update-readme
  3. 修改一个或多个文件
  4. 保存这些文件
  5. 将应包含在下次提交中的文件或代码片段加入暂存:git add README.md
  6. 提交变更:git commit -m "update the README to include links to contributing guide"
  7. 推送变更到远端分支:git push -u origin update-readme

用多次git add拆分逻辑提交

git add更强大的用法是:在一次工作会话中,通过多次选择性暂存,把彼此无关的改动拆成多个语义清晰的提交:

  1. 创建分支:git branch update-readme
  2. 切换到该分支:git checkout update-readme
  3. 修改一个或多个文件
  4. 保存这些文件
  5. 只添加其中一个文件或该文件的一部分改动:git add README.md
  6. 提交第一组变更:git commit -m "update the README to include links to contributing guide"
  7. 再添加另一个文件或另一部分改动:git add CONTRIBUTING.md
  8. 提交第二组变更:git commit -m "create the contributing guide"
  9. (按需重复以上步骤)
  10. 推送变更到远端分支:git push -u origin update-readme

这正是 git-overview.md 所描述的基础 Git 工作流的落地:创建分支后,"要开始提交,你需要用git add [file]告诉 Git 你想包含哪些改动",随后再执行git commit -m "descriptive commit message"。对于全新初始化且尚无任何提交的仓库,git-init.md 给出的步骤同样以git add为起点:"用git add暂存现有文件,再用git commit创建快照",之后再git push -u origin main建立与远端的跟踪关系。

四、暂存全部文件:省时但需谨慎

"暂存所有可用文件"是一种流行但有风险的操作。它能节省时间,但风险主要有两方面。

风险一:历史缺乏深思熟虑

一次性暂存所有改动,你的提交历史的清晰度很可能会受损。塑造历史的能力是使用 Git 的最大优势之一。如果提交过于庞大、包含无关改动,或提交信息描述不清,你就会失去查看和修改历史所带来的全部收益。

风险二:意外暂存并提交了不该提交的文件

使用一次性添加所有文件的选项,你可能意外地把某个文件暂存并提交。大多数常见选项不会添加.gitignore中已跟踪排除的文件;但任何未列入.gitignore的文件都会被暂存并提交。这包括大型二进制文件,以及包含密码、认证令牌等敏感信息的文件。关于如何用.gitignore排除文件,可参见 Git 速查表 中"The .gitignore file"一节。

决定暂存全部文件时的三种选择

如果时机合适,需要暂存全部文件,有几种命令可选。一如既往,清楚自己暂存并提交了什么,至关重要。

  • git add -A:暂存所有文件——包括新增、修改和删除的文件;既包含当前目录下的文件,也包含更高层级目录中仍属于同一 Git 仓库的文件
  • git add .:递归添加整个目录,包括以点号(.)开头的文件(如.gitignore、.env)
  • git add -u:仅暂存已跟踪文件中被修改和被删除的文件,不包含新文件

三种方式的行为差异可通过下表精确对照:

命令新增文件修改文件删除文件以点号开头的文件当前目录更高层级目录
git add -A是是是是是是
git add .是是是是是否
git add -u否是是是是是

这张表的实际意义在于:git add .只作用于当前目录及其子目录(不会误伤仓库其他目录中的改动),而git add -A会覆盖整个仓库;git add -u则适合你只想提交"对已跟踪文件的修改、清理删除"而暂不纳入新文件的场景。

五、暂存指定文件夹或具体文件:最安全清晰的方式

使用git add最安全、最清晰的方式,是明确指定要暂存的文件或目录:

  • git add directory/:暂存名为directory的目录内所有文件的全部改动
  • git add README.md:暂存README.md文件内的全部改动

这种方式把"将要进入下次提交的内容"完全掌握在自己手中,是日常开发中最推荐的习惯。在动手之前,配合git status查看当前分支与暂存状态总是好习惯——git-status.md 指出git status会告诉你当前HEAD指向哪里、有哪些已修改文件、它们是否已暂存,以及本地分支与远端分支相比是领先还是落后。

六、撤销git add:把文件移出暂存区

在执行撤销之前,首先要确认你不会丢失任何工作。git add没有像撤销提交那样的"revert"机制,但你可以把文件移出暂存区。

一个需要特别警惕的场景:如果你已暂存某个文件,随后又在工作区对该文件做了更多修改,那么工作区版本与暂存区版本就会不一致。如果此时你把暂存区中的"变更版本"移除,那些只存在于工作区、尚未暂存的改动可能会被覆盖。

要避免这种情况,可以先把所有改动一起暂存、再一起取消暂存;或者先提交改动,再在提交之前用 reset 回退。

用git reset撤销git add

git reset是一个灵活而强大的命令,其众多用途之一就是把变更移出暂存区。要做到这一点,请使用 reset 的mixed级别——这也是它的默认级别。

要把暂存的变更从暂存区移回工作区(同时不影响已提交的历史),请先按上文所述确认相关文件没有额外的未暂存改动,然后执行:

git reset HEAD

这条命令等价于git reset --mixed HEAD。它只移动暂存区指针与文件状态,不会改动工作区文件内容,也不会改写提交历史,因此是撤销git add的安全方式。关于--soft、--mixed、--hard三种级别的取舍,仓库中的 git-commit.md 在讨论撤销提交时给出了同样的提醒:使用git reset前,务必与团队沟通共享提交、研究三种重置级别,并先提交任何不想丢失的工作——已提交的工作可以找回,未提交的工作无法找回。

七、与git add紧密相关的命令

命令作用
git status总是值得运行:显示你所在的分支、工作区与暂存区的文件状态以及其他重要信息。配合 git-status.md 阅读效果更佳
git checkout [branch-name]切换到指定分支并更新工作目录
git commit -m "descriptive message"将文件快照永久记录在版本历史中。提交前必须先git add,详见 git-commit.md
git push将本地分支的所有提交上传到远端,详见 git-push.md
git diff查看工作区、暂存区与提交之间的内容差异,用于确认git add之前到底改了什么

八、小结:把git add变成塑造历史的习惯

git add是 Git 提交两阶段模型(暂存 + 提交)中的第一环,也是唯一能精确控制"哪些改动进入哪个提交"的杠杆:

  • 精确暂存:git add <path>指定文件或目录,是最安全清晰的方式;
  • 拆分提交:git add -p交互式按块暂存,让同一个文件的不同逻辑改动进入不同提交;
  • 批量暂存:git add -A/git add ./git add -u各有行为边界,务必对照差异表选择,并用.gitignore守住敏感文件与二进制文件的底线;
  • 安全撤销:git reset HEAD(即--mixed默认级别)把文件移出暂存区,且不触碰工作区与历史。

这套方法论正是 GitHub Training Kit 系列指南(git-add.md、git-commit.md、git-status.md)与多语言 Git 速查表 反复强调的核心:提交信息应简洁、描述性、使用祈使句现在时(如git commit -m "update broken URL to Git resources"),而git add正是确保每次提交只包含一个逻辑变更单元、让历史真正"讲得清故事"的起点。从今天起,把"先想清楚再git add"变成你的肌肉记忆,你的仓库历史会感谢你。

  • 文档
  • 教程

【免费下载链接】training-kit

Open source courseware for Git and GitHub

项目地址:https://gitcode.com/gh_mirrors/tr/training-kit
点击查看免费下载

相关推荐

上一篇:Gutenberg 的 E2E 测试基座:@wordpress/e2e-test-utils-playwright 使用指南与源码解读
下一篇:Apache Pulsar Scalable Topics 客户端规范导读:范围界定、规范性语言与一致性约定

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进