相信不少同学初入团队时,都会被分配一个名为 ai_project 或类似名称的项目目录,然后开始在里面写代码。这个目录就是我们常说的项目开发目录,里面放满 HTML、CSS、JS 等文件。听起来很正常,对吧?但只用这样一个普通文件夹来管理代码,隐患其实非常多:
- 无法多人协作:每个人都在自己的电脑上修改,互相传文件,效率极低,而且极容易覆盖彼此的劳动成果。
- 单机版本难以追溯:一旦文件被改乱或误删,若没有备份就只能欲哭无泪。你根本不知道昨天的代码长什么样。
- 没有版本概念 :同一个文件可能有 N 个修改过的副本,比如
index-最新.html、index-最终版.html、index-打死也不改.html......但这些"版本"之间没有记录、没有对比,一旦出问题根本搞不清哪个才是正确的快照。 - 不够工程化:现代软件开发讲究自动化、规范化和可追溯,单纯用文件夹来管理根本无法满足。
正因如此,我们需要一个能记录每一次变更、支持多人并行开发、随时回溯历史 的工具------Git。
从中央仓库到本地仓库:Git 的分布式模型
Git 采用的是分布式版本控制 体系。在团队协作中,通常会有一个中央仓库(Remote) ,托管在 GitHub、Gitee 或私有 GitLab 上,相当于团队共享的"权威代码库"。而团队中每个成员的机器上,都会克隆(clone) 出一份完整的本地仓库(Local) ,包含了完整的版本历史。
这意味着:
- 即使中央仓库宕机,每个人的本地仓库也是一份完整备份。
- 你可以完全离线地提交、回退、创建分支,等有网络时再推送到远程。
- 每个成员可以在自己的分支上独立开发,最后再把成果合并回共享仓库。
git init:赋予项目版本控制能力
如果我们想把一个普通目录变成具有版本控制能力的代码仓库,第一步就是:
bash
csharp
git init
执行后,项目根目录下会多出一个名为 .git 的隐藏文件夹。在 Linux / macOS 的终端下用 ls -a,或者在 Windows 的 Git Bash 中(一个最简化的 Linux 环境),都能看到它。
之所以隐藏,是因为它的内容由 Git 全权管理,严禁手动修改 。所有暂存区、历史记录、分支信息等都存储在这里。一旦 .git 被损坏,整个仓库的版本信息就可能丢失,所以一定要尊重这个"黑盒子",只通过 Git 命令与之交互。
工作区、暂存区与版本库:理解文件流转
要真正用好 Git,必须理解三个核心区域:
- 工作区(Working Directory) :就是我们能直接看到和编辑的文件夹,比如
lms_ai目录下的所有文件。 - 暂存区(Stage / Index) :一个临时区域,用于选择哪些修改会在下一次提交中进入版本库。可以把它想象成购物车,你可以多次往里面添加商品,最后一次性结账。
- 版本库(Repository) :Git 真正存储提交历史的地方,位于
.git内部。只有commit操作才会把暂存区的内容永久记录为一个新版本。
git add:把修改加入暂存区
当我们新建或修改了文件后,第一步是把它们添加到暂存区:
bash
csharp
git add 文件名
此时,该文件会被 Git 跟踪,并且当前的内容被放入暂存区。执行成功后通常没有输出,但我们可以通过 git status 看到变化,它会提示类似这样的信息:
text
yaml
Changes to be committed:
modified: index.html
如果执行 git add 时使用了 -v 参数,还可能看到形如 2 insertions 的输出,表示该文件新增了两行内容。这里注意,insertions 不代表一定是绝对的新增行数,而是 Git 对比出的差异行数,对文本内容增删改都会分别统计插入和删除行数。
git commit:将暂存区提交为一个版本
确认所有需要的修改都加入了暂存区后,就可以执行:
bash
sql
git commit -m "描述信息"
-m 后面跟着的字符串就是本次提交的说明。这个说明不能随意乱写,因为团队 leader 和同事在查看提交历史时,主要是通过这个说明来理解"谁、在什么时候、做了什么"。一个好的提交信息通常是简明扼要且反映完整意图的,例如:
bash
sql
git commit -m "feat: 完成首页布局和样式"
一旦 commit 成功,暂存区的内容就被永久记录进了版本库,当前仓库的版本历史向前推进了一步。
为什么分两步:add + commit?
你可能想问,直接 commit 不行吗,为什么要先 add?原因在于:一次提交应该对应一个完整的、有意义的变更单元 。在实际开发中,我们常常需要同时修改多个文件才能完成一个功能。比如做一个首页,可能涉及 index.html、common.css 和 common.js 三个文件。
我们可以这样做:
bash
sql
git add index.html
git add common.css
git add common.js
# 此时检查一下暂存区是否正确,甚至可以在 commit 前随时反悔
git commit -m "首页整体功能实现"
通过分步操作,我们实现了多次 add,一次 commit 。这让每次提交都保持原子性和可读性,也给了我们在最终提交前"反悔"的机会(比如用 git reset HEAD 文件名 将文件移出暂存区),而不会污染仓库历史。
git status:时刻掌握仓库状态
在任何你不确定当前仓库处于什么状态的时候,第一反应都应该是:
bash
lua
git status
尤其是在 add、commit、切换分支、合并等关键操作前后,git status 是你的眼睛。它会清晰告诉你:
- 哪些文件是未跟踪的(Untracked files)
- 哪些文件已修改但未暂存(Changes not staged for commit)
- 哪些文件已暂存等待提交(Changes to be committed)
- 当前分支与远程分支的关系
养成这个习惯,能帮你避免大量不必要的错误。
文件状态的流转
Git 中文件的状态大致可以分为以下几种,它们之间会随着我们的操作而不断变化:
-
未跟踪(Untracked)
新建且从未
git add过的文件。Git 不会管理它。 -
已跟踪(Tracked)
已纳入 Git 管理的文件,又可分为:
- 未修改(Unmodified) :与版本库最新提交完全一致。
- 已修改(Modified) :文件内容发生了变化,但尚未
add到暂存区。 - 已暂存(Staged) :修改已经被
git add,暂存区已记录,等待commit。
一个常见的完整流转是:
text
sql
新建文件 → Untracked → git add → Staged → git commit → Unmodified
└→ 之后又修改 → Modified → git add → Staged → git commit → Unmodified
每次 commit 之后,仓库保持"干净"的状态,也就是 git status 显示"nothing to commit, working tree clean",这是一个良好的开发习惯。
小结
Git 是现代软件开发的基石,它让代码管理从单机手动备份进化到分布式、可追溯、可多人协作的工程化模式。今天这些最基础的操作------init、add、commit、status------虽然看似简单,却构成了 90% 日常开发中与 Git 的交互。理解工作区、暂存区、版本库三层模型,以及文件状态的流转,是掌握更高级特性的根基。