基本操作
本章要点
git init创建仓库、git clone克隆仓库- 日常三连:
git status→git add→git commit - 查看历史:
git log的各种姿势 - 查看差异:
git diff - 移动与删除文件:
git mv、git rm - 写好提交信息的方法论
获取仓库的两种方式
方式一:初始化新仓库
bash
$ mkdir my-project && cd my-project
$ git init
# Initialized empty Git repository in /path/to/my-project/.git/- 会在当前目录创建隐藏的
.git/目录,这就是版本库本体。 - ⚠️ 不要在已有的 Git 仓库内部再执行
git init(会创建嵌套仓库)。
方式二:克隆已有仓库
bash
$ git clone https://github.com/user/repo.git
$ git clone https://github.com/user/repo.git my-folder # 自定义目录名- 克隆 = 完整复制远程仓库的全部历史到本地。
- 会自动配置好名为
origin的远程仓库别名。
查看状态:git status
bash
$ git status # 详细状态
$ git status -s # 简短状态(short),一行一个文件-s 输出格式(两列分别表示暂存区和工作区的状态):
text
?? untracked.md # ?? = 未跟踪(Untracked)
A added.md # A = 已暂存(Staged/Added)
M modified.md # M = 已修改未暂存(Modified)
MM both.md # 左 M 已暂存的修改,右 M 工作区又有新修改
D deleted.md # D = 已删除但未暂存
R renamed.md # R = 重命名💡 状态字母速记:
??从未见过,A待提交,M有改动,D删除了。
暂存与提交
git add:把改动放入暂存区
bash
$ git add file.txt # 暂存单个文件
$ git add src/ # 暂存整个目录
$ git add . # 暂存当前目录下所有改动(⚠️ 注意别把密钥文件加进去)
$ git add -A # 暂存所有改动(含删除),等价于 git add .(部分旧版本差异)
$ git add -p # 交互式分块暂存(强大!后面详述)
$ git add --update # 只暂存已跟踪文件的修改(不包含新增未跟踪文件)git commit:固化快照
bash
$ git commit -m "提交说明" # 最常用
$ git commit # 打开编辑器写详细说明(适合长提交信息)
$ git commit -am "说明" # add + commit 一步完成(⚠️ 只对已跟踪文件生效,新增文件仍需 git add)
$ git commit --amend -m "新说明" # 修改上一次提交(见 6.6 节)提交信息规范(Commit Message)
好的提交信息让人一眼看懂历史,团队必须统一规范:
text
<type>(<scope>): <subject> # 第一行:标题,≤ 50 字符
<body> # 空一行后写正文:为什么改、怎么改常见 type(约定式提交 Conventional Commits):
| type | 含义 |
|---|---|
| feat | 新功能 |
| fix | 修复 bug |
| docs | 文档改动 |
| style | 格式(空格、分号等,不影响逻辑) |
| refactor | 重构(不改功能) |
| test | 测试相关 |
| chore | 构建/工具/依赖等杂项 |
| perf | 性能优化 |
| revert | 回滚某次提交 |
示例:
text
feat(login): 增加短信验证码登录
- 新增验证码发送接口 /api/sms/code
- 登录页支持手机号 + 验证码方式
- 验证码有效期 5 分钟,60 秒内不可重复发送💡 为什么需要规范?
git log和 Code Review 都依赖提交信息传达意图;自动生成 changelog 也需要(如 semantic-release)。
查看历史:git log
bash
$ git log # 完整历史
$ git log --oneline # 每行一条:缩写哈希 + 标题(最常用)
$ git log --oneline -10 # 只看最近 10 条
$ git log --graph # 带 ASCII 分支图(配合 --oneline --all --decorate 效果最佳)
$ git log -p # 同时显示每次提交的完整 diff
$ git log --stat # 显示每次提交改了哪些文件、增减行数
$ git log --author="张三" # 按作者过滤
$ git log --since="2 weeks ago" # 按时间过滤
$ git log --grep="fix" # 按提交信息关键字过滤
$ git log -- <文件> # 只查看某个文件的历史(注意 -- 后的空格)
$ git log -S "关键字" # 找出"新增或删除该字符串"的提交(pickaxe 搜索)
$ git log --oneline --follow -- <文件> # 跟踪文件重命名历史输出示例:
text
$ git log --oneline --graph
* 8f4a2c9 (HEAD -> main, origin/main) fix(login): 修复验证码 60 秒倒计时不刷新
* 3b1e7d0 feat(login): 增加短信验证码登录
* c9a21f4 docs: 更新 README
* 5d0e1a3 feat: 项目初始化💡
HEAD表示"当前所在的位置"(当前分支的最新提交)。HEAD -> main表示当前在 main 分支上。
查看某次提交的详细信息
bash
$ git show 8f4a2c9 # 查看该提交的改动
$ git show 8f4a2c9 --stat # 只看统计信息
$ git show HEAD # 查看最近一次提交查看差异:git diff
bash
$ git diff # 工作区 vs 暂存区(我改了什么还没 add)
$ git diff --staged # 暂存区 vs 版本库(我将要提交什么)
$ git diff HEAD # 工作区 vs 版本库(全部未提交的改动)
$ git diff <提交1> <提交2> # 两个提交之间的差异
$ git diff <分支A> <分支B> # 两个分支之间的差异
$ git diff --stat # 只显示统计
$ git diff -- <文件> # 只看某个文件⚠️ 新手最容易搞混:
git diff(不带参数)只看工作区里"还没 add"的改动,看不到已经 add 的内容;想看已暂存的内容要用git diff --staged。
彩色 diff 示例
diff
$ git diff
diff --git a/README.md b/README.md
index 3b18e51..d8f3a20 100644
--- a/README.md
+++ b/README.md
@@ -1,3 +1,4 @@
# 项目说明
-这是旧内容
+这是新内容
+新增了一行-开头:被删除的行(红色)+开头:新增的行(绿色)@@ -1,3 +1,4 @@:变更位置(旧文件第 1 行起 3 行,新文件第 1 行起 4 行)
查看待提交内容的便捷命令
bash
$ git diff --cached # 等价于 git diff --staged移动与删除文件
重命名/移动
bash
$ git mv old.txt new.txt # 重命名(同时暂存这个改动)
$ git mv src/a.js lib/a.js # 移动目录删除
bash
$ git rm file.txt # 删除文件并暂存删除操作(工作区和版本库同步删除)
$ git rm --cached file.txt # 只从版本库移除跟踪,保留本地文件(常用语把误提交的密钥移出跟踪)
$ git rm -r dir/ # 递归删除目录💡 不记得
git mv/git rm也没关系:直接mv/rm后执行git add -A,Git 会自动识别为重命名/删除。Git 本质上是靠内容相似度识别重命名的。
一次完整的工作循环演示
bash
$ cd my-project
$ git status -s # ?? hello.md
$ echo "Hello Git" > hello.md
$ git status -s # ?? hello.md(新文件默认未跟踪)
$ git add hello.md
$ git status -s # A hello.md(已暂存)
$ git commit -m "docs: 新增 hello.md"
# [main 4d2f1a3] docs: 新增 hello.md
# 1 file changed, 1 insertion(+)
$ echo "Hello Git World" > hello.md # 修改内容
$ git status -s # M hello.md(已修改未暂存)
$ git diff # 查看修改内容
$ git add hello.md && git commit -m "docs: 更新 hello.md"
$ git log --oneline # 查看历史交互式暂存:git add -p
git add -p 让你**分块(hunk)**决定哪些改动进暂存区,适合"一个文件里混着两个功能"的场景:
text
$ git add -p file.txt
@@ -1,7 +1,10 @@ ... # 第一个改动块
Stage this hunk [y,n,q,a,d,j,J,g,/,e,?]? # 按键选择常用按键:
| 按键 | 含义 |
|---|---|
y | 暂存这一块 |
n | 不暂存这一块 |
s | 把这一块再拆小 |
e | 手动编辑这一块(精细控制) |
q | 退出 |
💡 用
git add -p可以做到"一个提交只包含一个逻辑改动",让历史像书一样整洁。
