Git 本地版本管理
指令速览
| 指令 | 作用 |
|---|---|
git init | 初始化本地 Git 仓库 |
git status | 查看文件状态 |
git add 文件名 | 将指定文件添加到暂存区 |
git add . | 将所有修改添加到暂存区 |
git commit -m "提交信息" | 将暂存区更改提交到版本库 |
git commit | 打开编辑器编写详细提交信息 |
git log | 查看提交历史 |
git log --oneline | 简洁查看提交历史 |
git log --graph --all | 图形化查看所有分支历史 |
git reset --soft 哈希值 | 软回退,只回退版本库 |
git reset --mixed 哈希值 | 混合回退(默认),回退版本库和暂存区 |
git reset --hard 哈希值 | 硬回退,回退版本库、暂存区和工作区 |
git reset HEAD~n | 回退到当前版本前第 n 个版本 |
git restore 文件名 | 撤销工作区对文件的修改 |
git revert 哈希值 | 创建新提交撤销指定提交的更改 |
git rm --cached -r 路径 | 将文件从暂存区移除(保留工作区文件) |
本栏目将介绍如何使用 Git 在本地管理项目并管理本地的代码版本迭代
初始化项目
-
首先你要创建一个本地的项目文件夹
-
在文件夹中右击打开菜单并点击打开 Git Bash,输入
git init -
Git 会在本地创建一个
.git文件夹用于存储版本管理信息
Git 本地仓库结构
在使用 Git 时,我们要明白在本地的三个工作区域的关系:
-
工作区:你实际编码与工作的区域,这个区域就是项目文件夹下除了
.git文件夹之外的所有区域 -
暂存区:这个区域存储了你使用
git add添加的文件的信息,用于下一次 commit 使用(不明白 add 和 commit?之后会详细介绍)
-
版本库:存储了所有的代码历史版本(即每次 commit 提交的版本),其中有一个 HEAD 指针 来标识现在的版本
Git 本地管理的基本工作流程
-
在工作区中修改(这里的修改是广义上的修改,包括删除、新建、修改)文件
-
使用
git add添加改动到暂存区 -
使用
git commit生成新的代码版本到版本库
工作流的具体介绍
git status:检查文件状态
在一个初始化完成的仓库的 Bash 中使用 git status 可以查看文件的状态
git add:将文件的更改从工作区提交到暂存区
-
在你的 Git 仓库中新建一个文件,比如说
README.md,然后运行git status,你会发现输出显示README.md显示在 "Untracked files" 这一标签之下,说明 Git 已经检测到了这个新的文件,但是没有将这个文件列入到 Git 的版本控制中 -
运行
git add README.md,然后再运行git status,你会发现这个README.md显示在 "Changes to be committed" 这一标签之下,说明这个文件的新建已经被 add 指令列入到 Git 的暂存区,等待下一次版本提交 -
一般地,
git add .可以将所有的存在于工作区中的文件修改添加到暂存区
git commit:将暂存区的所有更改记录合成为一个版本并记录到版本库
我们在之前的操作之后运行 git commit -m "add README.md",然后运行 git status,你会发现输出显示 "nothing to commit, working tree clean",这说明暂存区中的所有提交都被合成了一个新的版本,并存储到了版本库中
git commit 的使用:
-
git commit不带参数执行时,会打开一个你选择的文本编辑器的窗口,里面的文本用于说明这次版本更新做了什么(这个文本编辑器是在安装时 Choosing the default editor used by Git 这边设置的,如果你忘记了设置为 VS Code,Git 就会使用默认的 Vim,你可能会发现 Vim 退不出来,这时候输入:wq再回车就行) -
-m参数用于直接在命令行中书写提示信息,就像之前那个示例指令一样,附加一个字符串即可
历史检查和版本回退
git log:查看提交历史
用于按时间倒序显示版本库中的版本
基本用法:
git log
输出包含每个提交的哈希值、作者、日期和完整的提交信息
注意这个哈希值,这个哈希值是这个版本的标识,在之后的版本回退中有用处
常用参数:
--oneline:将每个提交压缩到一行显示,只包含 SHA-1 值的前几位和提交主题--graph:在输出的左侧以 ASCII 图形的方式展示分支与合并历史--all:显示所有分支的历史,而不仅仅是当前分支
git reset:回退到某个版本
注意:对于已经推送到公共/共享仓库的提交,应避免使用
git reset,因为它会给协作者带来麻烦当然我们现在正在介绍本地版本管理工作流,在本地你可以随便使用
git reset(前提是你知道你在做什么)
git reset 有三种主要模式:
--soft:仅移动 HEAD 指针到指定的提交,暂存区和工作区的内容保持不变
即:只回退了版本库中的版本,但是工作区和暂存区保持原样
常用于取消这次的 commit
(比如说误提交版本或者想和之后的更新一起提交版本)
git reset --soft 版本哈希值(使用 git log 获取,一般来说前 6 位即可)
--mixed(默认模式):移动 HEAD 指针,并用指定提交的内容重置暂存区,工作区的内容保持不变
即:只回退了版本库和暂存区(相当于清空了暂存区,因为每次提交版本之后暂存区都是空的)中的内容,但是工作区保持原样
常用于取消这次的 commit 和 add
(比如说想把一次提交拆分为多个 add 并提交,或者失误将不应该放入暂存区的文件给 add 了)
git reset --mixed 版本哈希值
# 或者简写为
git reset 版本哈希值
--hard:移动 HEAD 指针,并用指定提交的内容重置暂存区和工作区
即:相当于将所有东西都回退到了目标版本,丢弃了目标版本到现在的所有更改
常用于回退代码到历史版本,特别好用!
(比如说你现在想要做一个新功能或者 debug,但是担心 AI 把你的代码改的一团糟,你可以先暂存一个目前的版本,然后如果 debug 失败,你的代码变成一坨了,你可以使用 reset --hard 回溯时间(笑))
git reset --hard 版本哈希值
版本哈希值也可以替换成 HEAD~n,用于回退到当前版本之前的第 n 个版本比如说 git reset HEAD~1 就是将版本库和暂存区回到最后一次提交的上一个提交
特别的,HEAD 表示最后一个版本,比如说 git reset --hard HEAD 就是抛弃工作区的所有更改,回到最后一个提交的版本
git restore:撤销工作区修改
如果您只是想撤销在工作区对某个文件所做的、但尚未暂存的修改,可以使用 git restore
即:仅更改工作区文件,但是不更改暂存区与版本库
git restore README.md
git revert:创建一个新的提交以撤销指定提交
与 git reset 不同,git revert 通过创建一个全新的提交来撤销某个历史提交的变更这个新提交的内容与被撤销的提交内容正好相反
优点: 它不会改变项目历史,是一种安全的撤销方式,特别适用于已经推送到共享仓库的提交
用法:
git revert 版本哈希值
执行后,Git 会打开文本编辑器,让您为这次 revert 操作编写提交信息,然后创建一个新的提交
特别注意一下 reset 和 revert 的区别!
reset 是 "回退",而 revert 是 "撤销" 回退就是回溯项目的历史到了目标版本,而撤销只撤销目标版本的更改
例如:git reset --hard HEAD~2 会将你的版本回退到 HEAD~2
而 git revert HEAD~2 仅仅只会撤回 HEAD~2 所做的更改!之后的 HEAD~1 和 HEAD 所做的更改仍然是保留的!
文件忽略机制
通常来说,下列文件不应该被列入版本管理之中,比如说:
- 编译产物(如
.dll,.exe) - 日志文件(
.log) - 依赖包目录(如
node_modules) - 包含敏感信息的配置文件
- 操作系统或编辑器生成的临时文件(如
.DS_Store)
此时,在仓库根目录下创建一个 .gitignore 文件,即可告诉 Git 忽略这些文件.gitignore 的语法规则如下:
- 以
#开头的行看作注释 - 可以使用标准的 glob 模式(简化版的正则表达式)
*匹配零个或多个字符?匹配一个字符/在模式末尾表示这是一个目录/在模式开头表示从项目根目录开始匹配!在模式开头表示取反(即使之前被其他规则忽略,也不忽略此模式匹配的文件)
例如:
# 忽略所有 .log 文件
*.log
# 忽略 build 目录下的所有内容
/build/
# 忽略 node_modules 目录
node_modules/
# 不忽略 example.log
!example.log
注意! .gitignore 只能对目前还没有 add 的文件起作用如果你不想添加的文件已经被添加到了暂存区,此时要先使用 git rm --cached -r path(其中 path 可以是文件路径或者目录路径)来将添加的文件从暂存区(也就是 cache)中移除
然后再在有 .gitignore 的工作区中运行 git add .,这样才可以忽略目标文件
注意! 一定要写 --cached,不然这个目标文件会在工作区,也就是你的本地目录中被删除
什么,你需要一个 .gitignore模板?为什么不试试gitignore.io呢 你可以在这个网站中输入你需要使用gitignore的仓库的语言,然后这个网站就会生成一份对应的gitignore模板 此外,github在新建仓库时也可以使用Add gitignore在仓库中添加模板