| 实用工具 , Git/Github , CLI(命令行)
类似 SourceTree
这样的图形化 Git 管理工具固然好用且高效,有时候我们还是需要使用命令行来执行一些操作。对于后端相关的工程师来说,在命令行中操作 Git 可能更为常见。
Ficow 也比较习惯了在命令行中操作 Git,所以在此梳理一份常用命令清单。如果有必要,我也会持续更新这篇文章。
如果您发现了什么错误,或者您有相关的操作技巧想分享,欢迎您给 Ficow 留言哈~
查看配置列表:
git config --list
配置姓名和邮箱地址,级别(global / system / local):
git config --local user.name "name"
git config --local user.email "email"
配置别名,使用 git logs 查看提交历史:
git config --global alias.logs 'log --pretty=oneline --graph --abbrev-commit'
配置HTTP登录校验方式的密码缓存到内存中,过期时间为15分钟:
git config --global credential.helper cache
全局配置更详尽的冲突内容:
git config --global merge.conflictstyle diff3
git init
git clone repo-url
建议使用 SSH 方式的链接,免输入账号和密码,非常高效!
添加远程仓库地址:
git remote add remote-repo-name url
,repo-name 通常为 origin
。
查看远程仓库信息:
git remote -v
git remote show remote-repo-name
,repo-name 通常为 origin
。
抓取所有分支的最新数据:
git fetch --all
列出本地分支的详细信息:
git branch -vv
查看远程分支:
git branch -r
为分支创建远程跟踪信息:
git branch -u remote-repo-name/branch-name
,remote-repo-name
通常为 origin
。git branch --set-upstream-to=remote-repo-name/branch-name local-branch-name
配置完毕之后,以后就可以直接使用 git pull
, git push
等命令与远程仓库进行数据同步。
移动HEAD的指向(切换分支):git checkout branch-name
用HEAD来替换INDEX和工作目录的内容(取消文件的所有更改):
git checkout file-name
git checkout file-path
常用 git checkout .
,等同于 git reset --hard .
:
创建并切换到该新分支:git checkout -b branch-name
只删除本地分支:git branch -D branch-name
删除远程分支:git push origin --delete branch
(只是移动指针,易找回数据)
或者git remote rm branch-name
直接删除远程分支
或者git branch -r -d origin/branch-name
先删除本地远程分支git push origin :branch-name
然后,再删除远程分支
添加轻量标签 v1.0.0:git tag v1.0.0
推送标签到远端:git push origin v1.0.0
删除标签:git tag -d tag-name
删除远端的标签:git push --delete origin tag-name
将 moving_branch
分支从 from_branch
变基到 to_branch
上:
git rebase —onto to_branch from_branch moving_branch
交互式的变基(可以高效地进行大面积的变基):git rebase -i new-base-branch
弹出的窗口(默认是 VIM 编辑器)中会显示类似如下内容:
pick bc40dbaa .......
pick 7a0d6ae3 .......
# Rebase 66a4a866..7a0d6ae3 onto 66a4a866 (3 commands)
#
# Commands:
# p, pick <commit> = use commit
# r, reword <commit> = use commit, but edit the commit message
# e, edit <commit> = use commit, but stop for amending
# s, squash <commit> = use commit, but meld into previous commit
# f, fixup <commit> = like "squash", but discard this commit's log message
# x, exec <command> = run command (the rest of the line) using shell
# b, break = stop here (continue rebase later with 'git rebase --continue')
# d, drop <commit> = remove commit
# l, label <label> = label current HEAD with a name
# t, reset <label> = reset HEAD to a label
# m, merge [-C <commit> | -c <commit>] <label> [# <oneline>]
# . create a merge commit using the original merge commit's
# . message (or the oneline, if no original merge commit was
# . specified). Use -c <commit> to reword the commit message.
#
# These lines can be re-ordered; they are executed from top to bottom.
#
# If you remove a line here THAT COMMIT WILL BE LOST.
#
# However, if you remove everything, the rebase will be aborted.
#
如果要移除某个 commit,就将 pick 改为 d 或者 drop。如果使用的是 VIM 编辑器,使用 :wq
进行保存即可。如果要放弃修改,使用 :q
。
测试会被删除的文件:git clean -n
强制性地递归删除目录、文件:git clean -fd
压栈所有未提交的内容:git stash push -m "message"
应用上一次压栈的内容,但不清除已压栈的内容(推荐优先使用):git stash apply 0
应用并弹出上一次压栈的内容(不推荐):git stash pop
显示压栈列表:git stash list
丢弃压栈内容:git stash drop stash{x}
清理压栈内容:git stash clear
追加文件(没有文件就跳过):git add file/path
修改提交记录:git commit --amend
如果需要将最新的改动推送到远端,需要使用强制推送(谨慎操作):git push --force
只撤销commit:git reset --soft HEAD~
撤销commit和add到Index的变更:git reset --mixed HEAD~ 等同于 git reset HEAD~
撤销commit, add 以及 撤销工作目录的变更(危险操作!!!):git reset --hard HEAD~
,此操作会销毁数据,如果文件提交过,可以通过reflog找回,否则无法找回。
工作目录中当前文件和暂存区域快照之间的差异:git diff
已经暂存起来的文件和上次提交时的快照之间的差异:git diff --cached
查看 diff 工具的帮助,了解可用的 diff 工具:git difftool --tool-help
指定 diff 工具,如 opendiff
:git difftool --tool=opendiff
输出 dev 分支基于 master 分支开发后的各种变动:git diff master...dev
查看具体改动:git diff hash1 hash2 --stat
git diff hash1 hash2 file-name
git difftool --tool=opendiff hash1 hash2 file-name
git add [file/directory]
git commit
git commit -m 'message'
添加 -a
参数可以顺便执行 git add .
,提交所有已修改的文件:
git commit -a -m 'message'
最简形式:
git log
输出 B 分支中有,而 A 分支中没有的提交记录:git log A..B
输出 A 和 B 分支中 彼此不包含的提交记录:git log A...B
如果对 ..
和 ...
感兴趣,您可以阅读这个解答。
将每个提交放在一行显示,这在提交数很大时非常有用。选项:oneline ,short,full 和 fuller:
git log --pretty=oneline
定制要显示的记录格式,这样的输出便于后期编程提取分析:
git log --pretty=format:"%h - %an, %ar : %s"
选项 说明 (作者指的是实际作出修改的人,提交者指的是最后将此工作成果提交到仓库的人)
%H 提交对象(commit)的完整哈希字串
%h 提交对象的简短哈希字串
%T 树对象(tree)的完整哈希字串
%t 树对象的简短哈希字串
%P 父对象(parent)的完整哈希字串
%p 父对象的简短哈希字串
%an 作者(author)的名字
%ae 作者的电子邮件地址
%ad 作者修订日期(可以用 -date= 选项定制格式)
%ar 作者修订日期,按多久以前的方式显示
%cn 提交者(committer)的名字
%ce 提交者的电子邮件地址
%cd 提交日期
%cr 提交日期,按多久以前的方式显示
%s 提交说明
显示分支图:
git log --pretty=oneline --graph --abbrev-commit
选项 说明
-p 按补丁格式显示每个更新之间的差异。
--stat 显示每次更新的文件修改统计信息。
--shortstat 只显示 --stat 中最后的行数修改添加移除统计。
--name-only 仅在提交信息后显示已修改的文件清单。
--name-status 显示新增、修改、删除的文件清单。
--abbrev-commit 仅显示 SHA-1 的前几个字符,而非所有的 40 个字符。
--relative-date 使用较短的相对时间显示(比如,“2 weeks ago”)。
--graph 显示 ASCII 图形表示的分支合并历史。
--pretty 使用其他格式显示历史提交信息。可用的选项包括 oneline,short,full,fuller 和 format(后跟指定格式)。
2小时内的提交:
git log --since=2.hours
选项 说明
-(n) 仅显示最近的 n 条提交
--since, --after 仅显示指定时间之后的提交。
--until, --before 仅显示指定时间之前的提交。
--author 仅显示指定作者相关的提交。
--committer 仅显示指定提交者相关的提交。
初始化空的子模块(克隆项目后,初次加载子模块),或者 git clone --recursive URL
克隆时初始化子模块:git submodule init
更新子模块:git submodule update --remote
重置子模块的改动:git submodule update
或者git submodule update -f --init
进行强制操作
通过二分查找来确定BUG在哪一次提交中引入
开始二分查找:git bisect start
标记当前的提交为有问题的版本:git bisect bad
标记 99d9b39 这次提交为正常的版本:git bisect good 99d9b39
标记好 bad 和 good 之后,git 就会输出 正常
版本和 异常
版本二者最中间的版本,测试该提交是否可以工作即可缩小 bug 的引入范围。
重置HEAD指针(退出二分查找模式):git bisect reset
只要本地的操作记录没有被删除,我们就可以用 reflog 回滚 git 操作:git reflog
找到你想回滚的 commit id,然后执行:git reset commit-id --hard
一切就恢复到之前的样子!Git 的世界,reflog 就是后悔药~
命令有点多,有些甚至并不是那么常用。但是,Ficow 认为这些命令在关键时刻可以非常高效!比如:git rebase -i,git bisect,等等。
工欲善其事必先利其器,Git 是我们开发工作中的日常小伙伴。和它玩熟一点,生活都会惬意很多呢~ 😄
参考内容:
Git Reference
Git - Rebase
What are the differences between double-dot “..” and triple-dot “…” in Git commit ranges?
觉得不错?点个赞呗~
转载声明:本站文章如无特别说明,皆为原创。转载请注明:Ficow Shen's Blog