0%

Git和SVN

Git和SVN

公司里常用的两种版本控制工具:Git和SVN,两者最大的区别就是Git是分布式,SVN是集中式。集中式的版本控制系统都有一个单一的集中管理的服务器,保存所有文件的修订版本,而协同工作的人们都通过客户端连到这台服务器,取出最新的文件或者提交更新。 分布式的版本控制系统都有一个单一的集中管理的服务器,保存所有文件的修订版本,而协同工作的人们在自己本地也会创建一个库,用于保存自己的修改与提交,之后再将自己库提交至服务器库进行更新。

Subversion的特点概括起来主要由以下几条:

  • 每个版本库有唯一的URL(官方地址),每个用户都从这个地址获取代码和数据;
  • 获取代码的更新,也只能连接到这个唯一的版本库,同步以取得最新数据;
  • 提交必须有网络连接(非本地版本库);
  • 提交需要授权,如果没有写权限,提交会失败;
  • 提交并非每次都能够成功。如果有其他人先于你提交,会提示“改动基于过时的版本,先更新再提交”… 诸如此类;
  • 冲突解决是一个提交速度的竞赛:手快者,先提交,平安无事;手慢者,后提交,可能遇到麻烦的冲突解决;

Git具有以下特点:

  • Git中每个克隆(clone)的版本库都是平等的。你可以从任何一个版本库的克隆来创建属于你自己的版本库,同时你的版本库也可以作为源提供给他人,只要你愿意;
  • Git的每一次提取操作,实际上都是一次对代码仓库的完整备份;
  • 提交完全在本地完成,无须别人给你授权,你的版本库你作主,并且提交总是会成功;
  • 甚至基于旧版本的改动也可以成功提交,提交会基于旧的版本创建一个新的分支;
  • Git的提交不会被打断,直到你的工作完全满意了,PUSH给他人或者他人PULL你的版本库,合并会发生在PULL和PUSH过程中,不能自动解决的冲突会提示您手工完成;
  • 冲突解决不再像是SVN一样的提交竞赛,而是在需要的时候才进行合并和冲突解决;
  • Git 也可以模拟集中式的工作模式,Git版本库统一放在服务器中,Git 的集中式工作模式非常灵活;
  • 可以为 Git 版本库进行授权:谁能创建版本库,谁能向版本库PUSH,谁能够读取(克隆)版本库;
  • 团队的成员先将服务器的版本库克隆到本地;并经常的从服务器的版本库拉(PULL)最新的更新;
  • 团队的成员将自己的改动推(PUSH)到服务器的版本库中,当其他人和版本库同步(PULL)时,会自动获取改变;
  • 你完全可以在脱离Git服务器所在网络的情况下,如移动办公或出差时,照常使用代码库;
  • 你只需要在能够接入Git服务器所在网络时,PULL和PUSH即可完成和服务器同步以及提交;
  • Git提供 rebase 命令,可以让你的改动看起来是基于最新的代码实现的改动;
  • Git 有更多的工作模式可以选择,远非 Subversion可比;
  • Git 分支是指针指向某次提交,而 SVN 分支是拷贝的目录,这个特性使 Git 的分支切换非常迅速,且创建成本非常低;

Git基本概念和常用命令

  • 工作区:就是你在电脑里能看到的目录。
  • 暂存区:英文叫 stage 或 index。一般存放在 .git 目录下的 index 文件(.git/index)中,所以我们把暂存区有时也叫作索引(index)。
  • 版本库:工作区有一个隐藏目录 .git,这个不算工作区,而是 Git 的版本库,版本库可分为远程仓库和本地仓库。
    220512-Git和SVN-1.jpg

Git 常用的是以下 6 个命令:git clonegit pushgit addgit commitgit checkoutgit pull
220512-Git和SVN-2.jpg

git 创建仓库的命令:

命令 说明
git init 初始化仓库
git clone 拷贝一份远程仓库,也就是下载一个项目。

提交与修改的命令:

命令 说明
git add 添加文件到暂存区
git status 查看仓库当前的状态,显示有变更的文件。
git diff 比较文件的不同,即暂存区和工作区的差异。
git commit 提交暂存区到本地仓库。
git reset 回退版本。
git rm 删除工作区文件。
git mv 移动或重命名工作区文件。

提交日志的命令:

命令 说明
git log 查看历史提交记录
git blame 以列表形式查看指定文件的历史修改记录

远程操作的命令:

命令 说明
git remote 远程仓库操作
git fetch 从远程获取代码库
git pull 下载远程代码并合并
git push 上传远程代码并合并

Git 分支管理:https://www.runoob.com/git/git-branch.html
Git 查看提交历史:https://www.runoob.com/git/git-commit-history.html
Git 标签:https://www.runoob.com/git/git-tag.html
更多命令查看Git完整命令手册地址:http://git-scm.com/docs

Tortoise SVN

SVN教程:https://www.runoob.com/svn/svn-tutorial.html

TortoiseSVN 是 SVN(Subversion) 版本控制系统的一个免费开源客户端,可以超越时间的管理文件和目录。TortoiseSVN 使用教程:https://www.runoob.com/svn/tortoisesvn-intro.html

企业通常是使用TortoiseSVN提供的图像化界面操作,使用较简单。Windows的Git提供了GitGUI,也可以使用TortoiseGit,配置参数也有图形化界面,之前实习的一家公司就是 TortoiseGit 和 TortoiseSVN 。

版本管控工具分支管理

SVN分支管理策略

  • trunk(主干|主线|主分支):是用来做主方向开发的,新功能的开发应放在主线中,当模块开发完成后,需要修改,就用branch。
  • branches(分支):分支开发和主线开发是可以同时进行的,也就是并行开发,分支通常用于修复bug时使用。
  • tags (标记):用于标记某个可用的版本,可以标记已经上线发布的版本,也可以标记正在测试的版本,通常是只读的。

branch是用来做并行开发的,这里的并行是指和trunk进行比较。比如,3.0开发完成,这个时候要做一个tag,tag_release_3_0,然后基于这个tag做release,比如安装程序等。trunk进入3.1的开发,但是3.0发现了bug,那么就需要基于tag_release_3_0做一个branch,branch_bugfix_3_0,基于这个branch进行bugfix,等到bugfix结束,做一个tag,tag_release_3_0_1,然后,根据需要决定branch_bugfix_3_0是否并入trunk。

Git分支管理策略

Git Flow模型中定义了主分支和辅助分支两类分支。其中主分支用于组织与软件开发、部署相关的活动,辅助分支组织用于解决特定的问题而进行的各种开发活动。Git Flow开发模型从源代码管理角度对通常意义上的软件开发活动进行了约束,为软件开发提供了一个可供参考的管理模型。Git Flow开发模型让代码仓库保持整洁,让小组各个成员之间的开发相互隔离,能够有效避免处于开发状态中的代码相互影响而导致的效率低下和混乱。

Git Flow模型的特点是只有2个主干分支,Master和Develop分支:Master分支上只有稳定的生产版本,Develop分支用于集成。其中还涉及到HotFix分支。而其他还有三类分支:Feature分支用于开发人员各自开发;Release用于代码合并和集成;HotFix用于产品版本代码的紧急修订。

master分支通常只能从其它分支合并,不能在master分支直接修改。master分支上存放的是随时可供在生产环境中部署的代码(Production Ready state)。当开发活动到一定阶段,产生一份新的可供部署的代码时,master分支上的代码会被更新。同时,每一次更新,最好添加对应的版本号标签(TAG),所有在Master分支上的Commit应该打Tag。

develop分支是保持当前开发最新成果的分支,一般会在此分支上进行晚间构建(Nightly Build)并执行自动化测试。develop分支产生于master分支, 并长期存在。当一个版本功能开发完毕且通过测试功能稳定时,就会合并到master分支上,并打好带有相应版本号的tag。develop分支是主开发分支,包含所有要发布到下一个Release的代码,主要合并其它分支,比如Feature分支。

辅助分支是用于组织解决特定问题的各种软件开发活动的分支。辅助分支主要用于组织软件新功能的并行开发、简化新功能开发代码的跟踪、辅助完成版本发布工作以及对生产代码的缺陷进行紧急修复工作。辅助分支通常只会在有限的时间范围内存在。辅助分支包括用于开发新功能时所使用的feature分支,用于辅助版本发布的release分支,用于修正生产代码中的缺陷的hotfix分支。辅助分支都有固定的使用目的和分支操作限制。通过对分支的命名,定义了使用辅助分支的方法。

feature分支可以从develop分支派生。feature分支的命名可以使用除master,develop,release-*,hotfix-*之外的任何名称。feature分支(topic分支)通常在开发一项新的软件功能的时候使用,分支上的代码变更最终合并回develop分支或者干脆被抛弃掉(例如实验性且效果不好的代码变更)。一般而言,feature分支代码可以保存在开发者自己的代码库中而不强制提交到主代码库里。Feature分支开发完成后,必须合并回Develop分支,合并完分支后一般会删feature分支,但也可以保留。

release分支可以从develop分支派生。release分支是为发布新的产品版本而设计的。在release分支上的代码允许做测试、bug修改、准备发布版本所需的各项说明信息(版本号、发布时间、编译时间等)。通过在release分支上进行发布相关工作可以让develop分支空闲出来以接受新的feature分支上的代码提交,进入新的软件开发迭代周期。当develop分支上的代码已经包含了所有即将发布的版本中所计划包含的软件功能,并且已通过所有测试时,可以考虑准备创建release分支。而所有在当前即将发布的版本外的业务需求一定要确保不能混到release分支内(避免由此引入一些不可控的系统缺陷)。成功的派生release分支并被赋予版本号后,develop分支就可以为下一个版本服务。版本号的命名可以依据项目定义的版本号命名规则进行。发布Release分支时,合并Release到Master和Develop, 同时在Master分支上打个Tag记住Release版本号,然后就可以删除Release分支。

hotfix分支可以从master分支派生。hotfix分支是计划外创建的,可以产生一个新的可供在生产环境部署的软件版本。当生产环境中的软件遇到异常情况或者发现了严重到必须立即修复的软件缺陷时,就需要从master分支上指定的TAG版本派生hotfix分支来组织代码的紧急修复工作。优点是不会打断正在进行的develop分支的开发工作,能够让团队中负责新功能开发的人与负责代码紧急修复的人并行的开展工作。hotfix分支基于Master分支创建,开发完后需要合并回Master和Develop分支,同时在Master上打一个tag。

使用Git遇到的问题

Git tag

参考:GIT 中如何打标签(git tag)

220512-Git和SVN-3.jpg

Git show

给历史版本打标签时用的commit可以通过git show查看历史版本的hash。

220512-Git和SVN-4.jpg

Git log

查看提交日志,当你要修改历史提交前,你可以通过git log看看要修改第几次的提交。

220512-Git和SVN-5.jpg

Git rebase

通过git rebase可以修改历史的版本,参考:Git系列之修改历史提交信息,使用rebase指令后会在vi编辑器中选择要修改哪次提交,然后通过vi编辑器修改提交的内容。

注意:异常退出可能导致文件丢失,不要慌终端有提示如何恢复。

220512-Git和SVN-6.jpg