Git 笔记:常用命令与原理

一、安装 Git

  • Windows:下载并安装 Git.
  • Mac:使用 Homebrew, MacPorts 或者下载 安装程序
  • Linux (Ubuntu, Debian):sudo apt-get install git-core
  • Linux (Fedora, Red Hat, CentOS):sudo yum install git-core

二、设置 Git

如果需要使用 SSH 协议连接

添加 SSH-Key

ssh-keygen -t rsa -C "[email protected]" # 第一次添加,key generator(密匙生成器)、rsa 一种算法
ssh-keygen -t rsa -f ~/.ssh/id_rsa_x -C "[email protected]" # 非第一次添加
cd ~/.ssh
open ~/.ssh # mac 下打开

SSH Key 是一对,分为私钥和公钥,是非对称加密,当本地仓库需要往远程仓库 push 时,私钥加密传输内容,而只有对应的公钥才能解密,所以远程仓库需要添加公钥。

一台电脑要连多个远程仓库,可以就用一对 SSH Key。如果在一台电脑上,要为不同远程仓库对应不同私钥时,需要新增 config 文件,为不同远程仓库指定使用不同的私钥。

# 第一个账号,默认使用的账号
Host github.com
HostName github.com
User git
IdentityFile ~/.ssh/id_rsa

# 第二个账号
Host second.github.com # second 为前缀名,可以任意设置
HostName github.com
User git
IdentityFile ~/.ssh/id_rsa_2

# 第三个账号
Host e.coding.net
User git
IdentityFile ~/.ssh/id_rsa_3
  • 原理分析:本地 SSH 客户端(Git)使用类似 [email protected]:deppwang/deppwang.github.io.git 地址来连接远程仓库(可通过 git remote 命令查看)。@ 后面跟的是 Host@github.com 代表使用 id_rsa 这个私钥

测试 SSH-Key

# 清空本地的 SSH 缓存,添加新的 SSH 密钥 到 SSH agent 中
ssh-add -D
ssh-add id_rsa
ssh-add id_rsa_x

ssh-add -l # 最后确认一下新密钥已经添加成功

ssh -T [email protected] # 测试是否连接成功

用户配置

# 全局配置 用户名 / 邮箱
git config --global user.name "Your Name"
git config --global user.email "[email protected]"

# 取消全局 用户名 / 邮箱 配置
git config --global --unset user.name
git config --global --unset user.email

# 进入项目文件夹,单独设置每个 repo 用户名 / 邮箱
git config user.email "[email protected]"
git config user.name "xxxx"

# 设置使用 https 使用代理
git config --global http.proxy socks5://127.0.0.1:1080
git config --global https.proxy socks5://127.0.0.1:1080
git config --list # 查看当前仓库所有配置

git config --global color.ui true # 显示颜色

LF 与 CRLF

  • LF (Line Feed) 代表换行,对应字符 \n,Unix 系统使用;CR(Carriage Return) ,CRLF 对应字符 \r,Windows 系统使用

    标准化 指在提交代码到 Git 版本库中时,将文本文件中的换行符 CRLF 转为 LF 的过程
    转换 指在检出 Git 版本库代码过程中,将文本文件中的换行符 LF 转换为 CRLF 的过程

git config --global core.autocrlf  [true | input | false]  # 全局设置
git config --local core.autocrlf [true | input | false] # 针对本项目设置
  • true 自动完成标准化与转换
  • input 只做标准化操作,不做转换操作
  • false 提交与检出的代码都保持文件原有的换行符不变

Git 安装后默认为 false,常用设置:

git config --global core.autocrlf  true # Windows
git config --global core.autocrlf input # Unix

配置别名

git config --global alias.st status
git config --global alias.co checkout
git config --global alias.ci commit
git config --global alias.br branch
git config --global alias.unstage 'reset HEAD'
git config --global alias.last 'log -1'
git config --global alias.lg "log --color --graph --pretty=format:'% Cred% h% Creset -% C(yellow)% d% Creset % s % Cgreen(% cr) % C(bold blue)<% an>% Creset' --abbrev-commit"

# macOS 版 Git 默认设置的别名
git config --global alias.aa '!git add . && git add -u . && git status'
git config --global alias.d diff
git config --global alias.cm 'commit -m'

三、常用命令

远程

git remote add origin [email protected]:username/repo.git # 关联远程库,可关联多个
git remote # 查看远程库
git remote -v # 查看更详细信息
git remote rename origin orgin2 # origin 重命名为 origin2

git co -b dev origin/dev # 将远程 dev 分支切换为本地 dev 分支

git push origin (-u) <branch-name> # 推送到远程分支,'-u' 参数,将当前分支和远程的 master 分支关联起来。不能 push 空到远程去
git push origin :branch-name /git branch -dr <remote/branch> # 删除远程分支
git push -f origin master # 回滚远程分支,让其跟本地分支一致

git pull # pull 所有的分支到本地,如果不是直接 clone 的项目,直接使用此命令会报错
git fetch # 拉取所有分支到本地,不 merge

git clone [email protected]:username/repo.git # clone 后 不用再关联远程库
git clone [email protected]:username/repo.git new-name # 将克隆的仓库重命名为 new-name

# 建立本地分支和远程分支的关联,git pull 失败时执行
git br --set-upstream-to=origin/branch-name branch-name
git br --set-upstream branch-name origin/branch-name

常规

git add . /git add -A  /git add --all # 添加所有的文件
git add -u # update,add 所有 modified 文件

git st # 查看状态

git ci -m <message> # Commit
git ci --amend --author="Author Name <[email protected]>" --no-edit # 修改最后一次 commit 的作者和邮箱,已提交到远程的 commit 不要修改

git rebase origin/master # 将当前分支 commit 链接到远程 master 分支后,让分支变为一根直线,更加清晰
git rebase --continue # 解决冲突后,无需 commit,此命令恢复原来 commit
git rebase --skip # 存在多个 commit 时,可能多个 commit 均需要解决冲突,此命令可跳过 commit,相当于删除 commit
git rebase --abort # 取消 rebase

git merge dev # 将 dev 分支合并到当前分支(默认 Fast-forward 模式,看不出来合并历史)
git merge --no-ff -m "merge with no-ff" dev # 禁用 Fast-forward,可以看出合并历史

git diff <file> # 查看修改的内容 (工作区和暂存区的不同,工作区和原来的不同)
git diff HEAD -- <file> # 查看工作区与版本库最新版本(分支的最新 commit)的不同
git diff --cached <file> # 查看暂存区和分支的不同

git log -p <file> # 查看当前文件 commit 记录
git log -p -1 # 查看最近一次 commit 修改记录
git blame <file> # 查看当前文件被谁修改过

Ctrl + C # 命令错误时,退出编辑页面
Ctrl + Z # 退出

分支

git br dev # 创建分支
git br -m oldName newName # 修改分支名字
git br # 查看当前分支
git br -v # 查看本地分支详情
git br -a # 查看所有分支
git br -av # 查看所有分支详情
git br -d dev # 删除 dev 分支,只是删除了 dev 指针。
git br -D <branch-name> # 强行删除没有合并的分支
git br | grep -v "dev" | xargs git branch -D # 删除除 dev 外的所有分支
git co -b dev # 创建并切换分支

撤销、删除与回退

git co -- <file> # 把文件在工作区的修改全部撤销掉(回到最近 git commit 或 git add 时的状态)
git co -- . # 全部撤销

git unstage <file> # 撤销 add 操作,将修改的内容放回工作区
git unstage . # 全部撤销

rm file # 删除工作区的文件,需要 commit 生效。删错了可以使用 `git co -- file` 还原
git rm --cached <file> # 从暂存区删除文件
git rm -rf --cached <file> # 从暂存区中清除文件文件
git rm <file> # 从分支上删除文件

git merge --abort # 撤销 pull/merge 操作,常用于 pull 冲突时

git reset --hard HEAD^ # 回退到上一版本
git reset --hard <commit> # 回退到某一版本
git reset --soft <commit> # 回退到某一版本,但不删除代码,可用于将多个 commit 合并为一个
git reflog show + git reset HEAD@{x} # 恢复回退代码

储藏

git stash save "message" # 把未提交的,当前现场「储藏」起来。
git stash list # 查看所有的 “储藏”
git stash apply # 恢复不删除
git stash drop ## 删除
git stash pop # 恢复顺便删除
git stash apply stash@{x} # 恢复指定下标 stash

标签

git tag <name> # 打标签
git tag # 查看所有标签
git tag <name> <commitId> # 将标签打在某个 commit 上
git show <name> # 查看标签信息
git tag -a <name> -m "***" <commitId> # -a 指定标签名,-
git tag -d <name> # 删除标签
git push origin --tags # 推送所有未推送的标签
git tag -d <name> /git push origin :refs/tags/<name> # 删除远程标签

.gitignore

# 忽略除 .sh/.py 结尾的其他文件
*
!*.sh
!*.py

项目协作时,本地修改某个文件,但不想将修改提交到远程。可以使用 「skip-worktree」来关闭 GIT 跟踪本地文件修改

git update-index --skip-worktree /Users/yanjie/Workspace/medweb/.PYTHON.sh

Commit

git ci -m "Article updated: `date +'% Y-% m-% d % H:% M:% S'`" # Article updated: 2019-05-29 21:11:06
git ci -m "`date +'% Y-% m-% d'`" # 2019-05-29
git ci -m "`date`"
current="`date +'% Y-% m-% d % H:% M:% S'`"
msg="Article updated: $current"
git ci -m "$msg" # Article updated: 2019-05-29 21:11:06
git ci -m ":bug: Fixing a bug." # 🐛 Fixing a bug.

IDEA Git

  • IDEA 版本控制是默认记录工作区和暂存区与分支上的不同,即:直接修改工作区的内容,不同;add 到暂存区后,还是不同
  • IDEA 可以直接 commit 文件而不用 add,可以理解为默认帮助 add
  • IDEA 的 revert 相当 git co -- file
  • 修改 commit 描述:Undo commit

四、原理

image.png

image.png

image.png

Rebase

References

评论默认使用 ,你也可以切换到 来留言。