为什么使用git
为什么我们要拥抱git呢?我们为什么花费精力去学习git的命令呢?
下面是描述git在工程中的使用场景和解决什么问题,规范等等,并不描述使用方法,想了解具体命令的推荐去看gitscm
官方文档
PS:我没有使用过svn进行版本管理工具,所以不去和svn进行对比
有人可能没有使用过版本管理工具,认为它太复杂,还需要花费相当大的精力来学习命令,仍然使用文件夹整体备份的方式来。
我们将会看到git可以怎样帮你管理修改历史并且有着更加强大的功能和应用场景,最重要的是可以和他人协作
git的优势
大量的开源项目使用git来做版本管理:linux kernel,android,busybox,[intel的项目],[redhat],google,这么多的project都在使用git来进行管理,学习使用这门工具是完全值得的。
使用git的的github平台上托管着大量开源项目,完全开放的,如果你想参与进来,首先从git clone
做起吧.
在git在工程中的应用
记录了一些使用git来解决工程问题,阅读源码等方面的功能,如果你也遇到了这样的问题,不妨试一试git
管理
在很多的IDE中已经集成了git工具,可以直接使用:Eclipse
,Visual Studio
git在工程中的应用
临时切换任务
你在某个项目下工作时,正在处理问题A,修改到一半,测试说出现了一个紧急BUG需要修复,现在你怎么办? 你可以选择使用下面的方式(任选其一)来帮助你将你的临时代码保存,只需要简单的敲几个命令就可以让你不再备份和还原整个工程。
git stash
git add & git commit && git checkout -b newbranch
git diff . > tmp.patch && git checkout .
理解源码
在Linux内核社区中linus说过这样一句话:READ THE FUCK SOURCE CODE(RTFSC)
,带着点色彩,不过很贴近事实。
linux内核开发注重这样一条原则,代码就是最好的注释
,一般的代码他们是不屑于写注释的,只有完成复杂功能的代码才需要注释。
当你阅读代码的时候,你很可能遇到非常多的不解的问题,如果你能找到人及时回到你的问题,恭喜你,太幸运了。不过很多时候我们需要自己去看一下代码。
作者在提交代码的时候往往是按照功能提交的,一个patch包含了功能完整的代码(理想状况),你可以找到这个patch的所有代码观察修改的那些位置,非常有用的方式。
git log
git blame
海量修改中快速定位问题提交
你的机器运行着内核版本3.10,你想要升级到3.18试试功能A是否好用,然后你原来的功能B不好用了,然后你需要查这个问题的原因。 你对B所涉及的领域不太懂,现学来不及啊,但是提交也太多了有几千个,不容易定位问题,那么你可以使用工程中的方法来定位问题。
通过二分法和测试结果结合起来逐步逼近出问题的点,可以更加快速的查找问题原因
$ git bisect start
$ git bisect bad # Current version is bad
$ git bisect good v2.6.13-rc2 # v2.6.13-rc2 is known to be good
$ git bisect reset # Quit the bisect session
$ git bisect run my_script arguments # Using script that tell good/bad
修改分享
当你和A合作完成一个功能时,你们两个分工合作,中间需要相互依赖。在某个时间点他想要试试你们两个的功能是否OK了,你可以将你的patch发送给A,然后他打上,你和它的代码就合体了。
git diff
功能合并
你和A分别完成不同的功能,你们在同样的一个code base上工作,在最后需要合并功能到一套代码中时,也许你会直接进行文件对比合并,不过下面的方式能够更加智能地合并和筛选出冲突
git rebase
git merge
多人分布式开发中review
当你的项目需要保证代码质量时,有人review过你的代码之后才能提交到公共的代码仓库。你可以使用如下的方式将你的patch提取出来发送给其他人,
其他人可以在后面加上Signed-off-by
表示review过了,一直传递到有人合并这个patch。
git format-patch,git am,git send-email:
图形化查看历史
对于新人比较友好的工具,将分支合并轨迹、提交记录可视化显示出来,也保留着搜索等功能,就是太吃资源了,cpu,内存占用较多。
gitk
版本回退
需要将代码回退到某个提交之后时,使用下面的方式就能简单回退
git revert
git使用规范流程
权限问题
裸的git服务中每个人都有权限提交到公共的代码仓库,各种未经审查的代码、花样百出的Bug可能就出现了,没错,大部分不是你的问题导致的。
1.可以通过一些代码审核服务:gitlab
,gerrit
等,git push
动作首先是推送到代码审核服务处,然后才能通过代码审核服务来提交到公共代码仓库。
在开源界特别是分布开发、人数较多的情况下,为开发者分配不同的角色,比较受大公司的欢迎。
2.还可以通过和大家共同约定规则,告诉所有人,只有部分开发者有权限合并代码并且会对此负责,其他人是不允许推送的。
将你的patch发送给指定的开发者和其他人,在经过充分的review之后才能提交到代码仓库。
这个最好适用于大家同处一个办公室或者一栋楼内,比较集中的开发环境、开发人员比较少时,依赖于整个团队对规则的遵守,问题也不大。
提交日志问题
对于大型的软件开发,特别是迭代比较多时,我们阅读前人写的代码时发现某一段看不懂,然后就不敢动这块代码,随着时间的推移,无用的代码越积越多,人为造成的软件体积增大。
可以通过规范提交日志来减缓这项问题,提交日志要反应提交的主要目的,对于某些微妙的bug需要加上详细的浮现步骤,日志等信息,目的就是帮助其他人理解你这块代码在解决什么问题。
有很多不同风格的commit规范,到哪座山唱哪首歌吧,和团队整体保持一致就好。
分支问题
我们经常会开发不同的功能,像linux内核开发中存在rc版本和稳定版本一样,我们开发的功能可能没有经过严格测试、整体测试一样,这个时候我们需要新建分支来存放我们的修改。
和分支相似的是tag,不过是有区别的
tag就像是一个里程碑一个标志一个点,branch是一个新的征程一条线;
tag是静态的,就是指向某个branch上的某个提交,而branch的HEAD是可以向前移动的;
稳定版本备份用tag,新功能多人开发用branch。