这次学习一下Git的一些高级点的功能。
本文主要参考http://stormzhang.com/github/2016/06/16/learn-github-from-zero5/
1. alias别名
git config --global alias.co checkout #别名
git config --global alias.cm commit
git config --global alias.st status
git config --global alias.br branch
当然以上别名不是固定的,你完全可以根据自己的习惯去定制,除此之外还可以设置组合,比如:
git config --global alias.psm 'push origin master'
git config --global alias.plm 'pull origin master'
之后经常用到的git push origin master 和 git pull origin master 直接就用 git psm 和 git plm 代替了。
下面这个命令可以把git log格式化
git config --global alias.log " log --graph --pretty=format:'%Cred%h%Creset -% C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit -- date=relative"
格式化后的效果如下:
其实还有一些有用的配置,进行下面的设置可以让终端显示不同的颜色:
git config --global color.ui true
git config --global core.quotepath false # 设置显示中文文件名
2. diff命令
使用diff命令可以在你提交前查看到底有哪些改动如:
红色部分代码是我删除的,绿色前面有个+号代码是我增加的。
git diff <$id1> <$id2> # 比较两次提交之间的差异
git diff <branch1>..<branch2> # 在两个分支之间比较
git diff --staged # 比较暂存区和版本库差异
3. checkout命令
checkout一般作为切换分支使用,如要切换到分支test,可以使用下面的命令:
git checkout test
但是checkout不只用作切换分支,也可以用来切换tag,切换到某次commit,如:
git checkout v1.0
git checkout ffd9f2dd68f1eb21d36cee50dbdd504e95d9c8f7 # 后面的一长串是commit_id,是每次commit的SHA1值,可以根据 git log 看到。
checkout除了有“切换”的意思还有还原的意思,假如代码还没有add进缓存区,可以直接把原文件还原:
git checkout a.md
4. stash命令
设想一个场景,假设我们正在一个新的分支做新的功能,这个时候突然有一个紧急的bug需要修复,而且修复完之后需要立即发布。当然你说我先把刚写的一点代码进行提交不就行了么?这样理论上当然是ok的,但是这会产品垃圾commit,原则上我们每次的commit都要有实际的意义,你的代码只是刚写了一半,还没有什么实际的意义是不建议就这样commit的,那么有没有一种比较好的办法,可以让我暂时切到别的分支,修复完bug再切回来,而且代码也能保留的呢?
这个时候 stash 命令就大有用处了,前提是我们的代码没有进行 commit ,哪怕你执行了 add 也没关系,我们先执行
git stash
命令,什么意思呢?意思就是把当前分支所有没有 commit 的代码先暂存起来,这个时候你再执行 git status 你会发现当前分支很干净,几乎看不到任何改动,你的代码改动也看不见了,但其实是暂存起来了。执行
git stash list
你会发现此时暂存区已经有了一条记录。
这个时候你可以切换会其他分支,赶紧把bug修复好,然后发布。之后一切都解决了,你再切换回来继续做你之前没做完的功能,但是之前的代码怎么还原呢?
git stash apply
你会发现你之前的代码全部又回来了,就好像一切都没发生过一样,紧接着你最好需要把暂存区的这次 stash 记录删除,执行:
git stash drop
就把最近一条的 stash 记录删除了,是不是很方便?其实还有更方便的,你可以使用:
git stash pop
来代替 apply 命令,pop 跟 apply 的唯一区别就是 pop 不但会帮你把代码还原,还自动帮你把这条 stash 记录删除,省的自己再 drop 一次了,为了验证你可以紧接着执行 git stash list 命令来确认是不是已经没有记录了。
最后还有一个命令介绍下:
git stash clear
就是清空所有暂存区的记录,drop 是只删除一条,当然后面可以跟 stash_id 参数来删除指定的某条记录,不跟参数就是删除最近的,而 clear 是清空。
5. merge & rebase命令
merge是分支合并的意思,假如branch1开发完了一个功能,我们要把这个功能同步到主干master上,可以执行下面的命令:
git checkout master
git merge branch1
rebase命令也是合并的意思,假如有二个书架上的书要合并,merge比较暴力就是直接腾出一块地方把另一个地方的书放过来。不过它的好处是你知道这些书是哪个书架上来的。rebase的话会对书进行比较,重新排序,然后重新放置好。缺点是这样放置后就不知道这本书是属于哪个书架了。
6. 解决冲突
以上截图里就是冲突的示例,冲突的地方由 ==== 分出了上下两个部分,上部分一个叫 HEAD 的字样代表是我当前所在分支的代码,下半部分是一个叫 baidu_activity 分支的代码,可以看到 HEAD 对 gradle 插件进行了升级,同时新增了一个插件,所以我们很容易判断哪些代码该保留,哪些代码该删除,我们只需要移除掉那些老旧代码,而且同时也要把那些 «< HEAD、==== 以及 »»»baidu_activity 这些标记符号也一并删除,最后进行一次 commit 就ok了。
7. 分支的常用操作
通常我们默认都会有一个主分支叫 master ,下面我们先来看下关于分支的一些基本操作:
新建一个叫 develop 的分支
git branch develop
这里稍微提醒下大家,新建分支的命令是基于当前所在分支的基础上进行的,即以上是基于 mater 分支新建了一个叫做 develop 的分支,此时 develop 分支跟 master 分支的内容完全一样。如果你有 A、B、C三个分支,三个分支是三位同学的,各分支内容不一样,如果你当前是在 B 分支,如果执行新建分支命令,则新建的分支内容跟 B 分支是一样的,同理如果当前所在是 C 分支,那就是基于 C 分支基础上新建的分支。
切换到 develop 分支
git checkout develop
如果把以上两步合并,即新建并且自动切换到 develop 分支:
git checkout -b develop
把 develop 分支推送到远程仓库
git push origin develop
如果你远程的分支想取名叫 develop2 ,那执行以下代码:
git push origin develop:develop2
但是强烈不建议这样,这会导致很混乱,很难管理,所以建议本地分支跟远程分支名要保持一致。
查看本地分支列表
git branch
查看远程分支列表
git branch -r
删除本地分支
git branch -d develop
git branch -D develop (强制删除)
删除远程分支
git push origin :develop
如果远程分支有个 develop ,而本地没有,你想把远程的 develop 分支迁到本地:
git checkout develop origin/develop
同样的把远程分支迁到本地顺便切换到该分支:
git checkout -b develop origin/develop