环境:当前
Git版本v2.49.0window
仓库
在当前目录初始化仓库
git init
创建目录并初始化仓库
git init [project-name]
拉取仓库
git clone [url]
拉取分支仓库
git clone -b [branch-name] [url]
配置
配置范围
系统级 (--system):影响整个系统的所有用户
全局级 (--global):影响当前用户的所有仓库
本地级 (--local):只影响当前仓库(默认)
优先级:local > global > system
查看当前Git的配置
git config -list
git config --global --list
git config --local --list
查看配置信息
git config user.name
git config --global uesr.name
git config --local user.name
编辑配置信息
git config --global [option] [value]
重要的配置项
git config --global user.name "Your Name" // 用户名
git config --global user.email "your.email@example.com" // 邮箱
git config --global core.editor "code --wait" // 打开 VScode 进行编辑
git config --global core.ignorecase false // 区分文件名大小写
git config --global init.defaultbranch main // 初始化仓库默认分支名
推送配置 push.default
推送模式:
// simple(新版本默认) - 推送当前分支到同名的上游分支(必须关联)
git config --global push.default simple
// matching(旧版本默认)- 推送所有匹配的分支
git config --global push.default matching
// current - 推送当前分支到同名远程分支(即使没有关联)
git config --global push.default current
// upstream - 推送到关联的上游分支(允许不同名)
git config --global push.default upstream
simple 模式
场景1:正常推送
git checkout -b branch
git push -u origin branch
git push
场景2:分支名不同会报错
git checkout -b branch
git push -u origin branch2
git push
拉取配置 pull.rebase false vs true
// 设置(默认)
git config --global pull.rebase false
// 相当于执行
git pull = git fetch + git merge
// 实际效果
// 本地: A---B---C (main)
// 远程: A---B---D---E (origin/main)
// 拉取后: A---B---C---D---E
// \ /
// + merge +
// 设置
git config --global pull.rebase true
// 相当于执行
git pull = git fetch + git rebase
// 实际效果
// 本地: A---B---C (main)
// 远程: A---B---D---E (origin/main)
// 拉取后: A---B---D---E---C (重新本地提交)
基础介绍
暂存区
# 添加指定文件到暂存区
$ git add [file1] [file2] ...
# 添加指定目录到暂存区,包括子目录
$ git add [dir]
# 添加当前目录的所有文件到暂存区
$ git add .
仓库区(本地仓库)
# 提交暂存区到仓库区
$ git commit -m [message]
# 提交暂存区的指定文件到仓库区
$ git commit [file1] [file2] ... -m [message]
# 使用一次新的commit,替代上一次提交
# 如果代码没有任何新变化,则用来改写上一次commit的提交信息
$ git commit --amend -m [message]
分支
# 查询本地所有分支
$ git branch
# 查询远程所有分支
$ git branch -r
# 查询所有本地分支和远程分支
$ git branch -a
# 新建一个分支,但依然停留在当前分支
$ git branch [branch-name]
# 新建一个分支,并切换到该分支
$ git checkout -b [branch](旧)
$ git switch -c [branch](新 推荐 更加语义化)
# 新建一个分支,指向指定commit
$ git branch [branch] [commit]
# 新建一个分支,与指定的远程分支建立追踪关系
$ git branch --track [branch] [remote-branch]
# 切换到指定分支
$ git checkout [branch-name](旧)
$ git switch [branch-name](新)
# 切换到上一个分支
$ git checkout -
# 建立追踪关系,在现有分支与指定的远程分支之间
$ git branch --set-upstream [branch] [remote-branch]
# 合并指定分支到当前分支
$ git merge [branch]
# 选择一个commit,合并进当前分支
$ git cherry-pick [commit1] [commit2] ...
$ git cherry-pick [commit1]..[commitN](不包含commit1)
$ git cherry-pick [commit1]^..[commitN](包含commit1)
$ git cherry-pick --continue // 解决冲突后继续
$ git cherry-pick --abort // 放弃本次操作
$ git cherry-pick --skip // 跳过当前提交
$ git cherry-pick -n <commit> // 只应用更改不提交
$ git cherry-pick -e <commit> // 编辑提交信息
# 删除本地分支
$ git branch -d [branch-name] // 删除已合并的分支
$ git branch -D [branch-name] // 强行删除未合并的分支
# 删除远程分支
$ git push origin --delete [branch-name]
# 清理本地过期的远程跟踪分支
$ git branch -dr [remote/branch] // 单个删除
$ git remote prune origin // 批量删除
储藏
# 查看储藏列表
$ git stash list
# 进行储藏
$ git stash -m [message] // 添加当前储藏的描述信息(推荐,方便恢复指定的储藏)
$ git stash // 没有描述信息
# 恢复最近的一次储藏(并保留储藏记录)
$ git stash apply
# 恢复最近的一次储藏(并删除储藏记录)
$ git stash pop
# 恢复指定的储藏(比如 stash@{1},需要查看当前有多少个储藏记录)
$ git stash apply stash@{1}
# 清除所有储藏
$ git stash clear
远程
# 下载远程仓库的所有变动
$ git fetch [remote]
# 显示所有远程仓库
$ git remote -v
# 显示某个远程仓库的信息
$ git remote show [remote]
# 增加一个新的远程仓库,并命名
$ git remote add [shortname] [url]
# 取回远程仓库的变化,并与本地分支合并
$ git pull [remote] [branch]
# 上传本地指定分支到远程仓库
$ git push [remote] [branch]
# 强行推送当前分支到远程仓库,即使有冲突
$ git push [remote] --force
# 推送所有分支到远程仓库
$ git push [remote] --all
# 强制推送到远程
$ git push --force origin [branch]
撤销
# 恢复暂存区的指定文件到工作区
$ git checkout [file]
# 恢复暂存区的所有文件到工作区
$ git checkout .
# 恢复某个commit的指定文件到暂存区和工作区
$ git checkout [commit] [file]
# 重置暂存区的指定文件,与上一次commit保持一致,但工作区不变
$ git reset [file]
# 重置暂存区与工作区,与上一次commit保持一致
$ git reset --hard
# 重置当前分支的指针为指定commit,同时重置暂存区,但工作区不变
$ git reset [commit]
# 重置当前分支的指针为指定commit,同时重置暂存区和工作区,与指定commit一致
$ git reset --hard [commit]
# 重置当前指针为指定commit,但保持暂存区和工作区不变
$ git reset --keep [commit]
# 新建一个commit,用来撤销指定commit
# 后者的所有变化都将被前者抵消,并且应用到当前分支
$ git revert [commit]
实际问题
切换分支,储藏代码,不提交
场景:当前正在 A分支 进行功能开发,突然有个紧急任务需要到 B分支 进行开发,但是当前 A分支 的功能还未开发完成,所以不希望进行提交,但是不进行提交就不能切换到 B分支,这时需要暂时将 A分支 的代码储藏起来,然后切换分支,等待 B分支 的任务完成在切换回来并且还原原本的 A分支 的代码
当前分支 A
# 储藏当前工作
git stash -m "功能开发到一半"
# 切换到B分支
git switch B
# 修复bug并提交...
# 完成后回到原分支
git switch A
# 恢复之前的工作
git stash pop
更改分支名
场景:更改本地分支名后,也需要同步远程的分支名的更改
# 1. 不在重命名的分支上
git branch -m [old-branch-name] [new-branch-name]
# 在重命名的分支上
git branch -m [new-branch-name]
# 2. 删除远程旧分支
git push origin --delete [old-branch-name]
# 3. 推送新分支到远程并建立联系
git push -u origin [new-branch-name]
本地与远程分支同步
场景:远程仓库分支被删,但是本地还未同步远程分支以及本地分支信息,需要更新本地的远程分支以及本地分支信息
# 1. 先拉取最新更改
git fetch origin
# 2. 删除所有远程不存在的跟踪分支
git fetch --prune origin
# 3. 同步删除本地分支(也可以不删除)
git branch -D [branch-name]
# 或者批量删除远程已经删除的本地分支
git branch -vv | grep ': gone]' | awk '{print $1}' | xargs git branch -D
撤销远程仓库的提交
方法一:
# 1. 查看提交历史
git log --oneline -n 3
# 输出:
# abc1234 错误的提交
# def5678 之前的提交
# ghi9012 更早的提交
# 2. 回退到上一个提交
git reset --hard def5678
# 3. 强制推送(会导致 def5678 后面的提交都被删除)
git push --force origin [branch-name]
方法二:
# 1. 查看要撤销的提交哈希
git log --oneline -n 3
# 输出:
# abc1234 错误的提交
# def5678 之前的提交
# ghi9012 更早的提交
# 2. 创建撤销提交
git revert abc1234
# 3. 提交信息
git commit -m "撤销错误的图片裁剪实现"
# 4. 正常推送(保留了之前的提交记录)
git push origin 分支名