SVN的使用(二)

来源:互联网 发布:nginx 显示目录结构 编辑:程序博客网 时间:2024/04/29 01:22

    第 2 章 基本概念-资料库
本文来自Svn中文网[www.svn8.com]转发请保留本站地址:
http://www.svn8.com/svnsy/20080202/10.html

本章是对Subversion的一个简短介绍。如果你是版本控制新手,那么本章正适合你读。我们从讨论版本控制的一般概念开始,然后深入到Subversion的一些特有想法,并演示一些应用Subversion的简单例子。

Svn中文网

虽然本章的例子是演示如何共享程序源码的,但请记住,Subversion可以管理任何种类的文件集--它不仅仅对计算机程序员有用。 Www.Svn8.Com

资料库Subversion是一个集中式信息共享系统。它的核心是作为数据存储中心的资料库。资料库以文件系统树--典型的文件和目录层次系统--的形式来存储信息。任意多个客户端都可连接到资料库,然后读写这些文件。通过写入数据,客户端可以共享信息给其他客户端,通过读出数据,客户端可以从别人那里得到信息。图 2.1 “一个典型的客户机/服务器 系统” 展示了这些: Svn8.Com

图 2.1. 一个典型的客户机/服务器 系统
Svn8.Com


哪为什么要这么做?到目前为止,这听起来就像一个典型的文件服务器的定义。确实,资料库是一种文件服务器,但不是通常的那种。Subversion资料库的特殊之处在于它会记住你对它所做的所有修改:对每一个文件的每一处改变,以及对目录树本身的改变,比如增加,删除,和重新安排文件和目录。 Svn8.Com

当一个客户端从资料库读文件时,通常只看到最新版的文件系统树。但是客户端也可以查看文件系统以前的状态。例如:客户端能问这样的历史性问题:“上星期三这个目录包含那些文件?”或者“谁是这个文件的上一个修改者,他们做了什么改动?”这类问题是所有版本控制系统的核心问题:系统要被设计为可以记录和追溯数据随时间的变化。

本文来自Svn中文网[www.svn8.com]转发请保留本站地址:http://www.svn8.com/svnsy/20080202/10.html

======
           版本模型
本文来自Svn中文网[www.svn8.com]转发请保留本站地址:
http://www.svn8.com/svnsy/20080202/11.html


版本控制系统的中心任务是使人们可以合作编辑和分享数据。但是不同的系统使用不同的策略来达到这一目的。

参考资料:www.svn8.com

文件共享的难题所有版本控制系统都必须解决相同的基本难题:如何使系统允许人们共享信息,又能防止人们意外互相干扰。由于不小心而覆盖了别人对资料库的改动这样的事太容易发生了。

Www.Svn8.Com

看看如图 2.2 “需要避免的问题”所演示的场景。假设有两个合作者,Harry和Sally。他们同时决定编辑相同的资料库文件。 如果Harry先把他的改动保存到资料库,那么可能(一段时间后)Sally会不小心用自己的新版文件覆盖了那些文件。虽然Harry版的文件不会丢失(因为系统记住了所有改动),但是Harry的任何改动都不会在Sally的新版文件中出现,因为她开始修改文件时并没有看到Harry的改动。Harry的工作从效果来看是丢失了,至少在最新版的文件里没有体现,可能只是处于偶然。这绝对是我们要避免地情形。won't be

Bbs.Svn8.Com

图 2.2. 需要避免的问题
参考资料:www.svn8.com


解决方案:锁定-修改-解锁很多版本控制系统用一种锁定-修改-解锁模型来解决这个难题。在这种系统中,资料库在某一时间只允许一个人修改某一文件。首先,Harry必须“锁定”这个文件,然后才能开始修改它。锁定一个文件有点像从图书馆里借书;如果Harry已经锁定了一个文件,那么Sally就不能对这文件作任何修改。如果她企图锁定这个文件,资料库将拒绝这个请求。她只能读这个文件,然后等Harry完成了他的修改并释放了他的锁。在Harry解锁了这个文件后,他这一轮修改结束了,现在Sally可以通过锁定和编辑来进行她这轮修改。图 2.3 “图2.3 解决方案:锁定-修改-解锁”展示了这个简单的解决办法 demonstrates this simple solution.

Bbs.Svn8.Com

图 2.3. 图2.3 解决方案:锁定-修改-解锁 Www.Svn8.Com

锁定-修改-解锁 模型的问题是它有点限制太强了,以至于常常成为人们的绊脚石:

Svn中文网

加锁可能引起管理上的问题。 有时Harry锁定了一个文件却忘了,Sally因为在一直等着修改这个文件,所以没法工作。接着Harry休假去了。现在Sally只好去找管理员来解开Harry的锁。这种情况会导致很多不必要的延误和时间上的浪费。 Www.Svn8.Com

加锁可能引起不必要的串行化。 如果当Harry在编辑一个文本文件的开头时, Sally只是想编辑同一文件的结尾时怎么办?这些修改根本不会互相交叠。他们可以同时编辑,如果修改能被恰当的合并,就不会有大的损害发生。在这种情况下没有必要非得轮着来。 Svn8.Com

加锁可能带来安全的错觉。 假如Harry锁定并编辑了文件A,同时Sally锁定并编辑了文件B。但是A和B是互相依赖的,从而对他们的改动在语义上无法兼容。这会导致突然间A和B不能一起工作了。加锁系统对阻止这样的问题发生无能为力,但是在一定程度上给人以安全的错觉。很容易导致Harry和Sally认为有文件锁定,他们做的是安全的,隔离的工作,犯不着提前讨论他们的互不兼容的修改。

Bbs.Svn8.Com

解决方案:拷贝-修改-合并Subversion,CVS,和其他一些版本控制系统使用拷贝-修改-合并模型,而不用加锁。在这个模型中,每个用户的客户端连接到项目资料库并创建一个个人的工作副本--资料库中文件和目录的本地映像。然后用户们并行的工作,修改他们私有的副本。最后这些私有副本被合并到一起成为一个新的最终的版本。版本控制系统通常会帮助做合并,但是根本上还是靠人来负责正确的合并。 Svn中文网

这里举一个例子。假如Harry和Sally都从资料库拷贝建立了同一项目的工作副本。他们并行的工作,分别对他们副本中相同的文件A做了修改。Sally先把她的修改保存到资料库中。当不久后Harry要保存他的修改时,资料库会通知他他的文件A过时了。换句话说,资料库中的文件A在他拷贝后有一些新的修改。于是,Harry让他的客户端程序把资料库中的修改合并到他的文件A的副本里。可能Sally的修改和他的不重叠,于是只要他合并了二者的修改,就可以把他的工作副本保存回资料库。 图 2.4 “解决方案:拷贝-修改-合并”和图 2.5 “解决方案:拷贝-修改-合并(续)”演示了这一过程。 Svn中文网

图 2.4. 解决方案:拷贝-修改-合并
Www.Svn8.Com

 

图 2.5. 解决方案:拷贝-修改-合并(续) Bbs.Svn8.Com

但是如果Sally的改动和Harry的有重叠怎么办?接下来呢?这种情况叫做冲突,通常不是什么大问题。当Harry让他的客户程序把资料库中最新的的修改合并到他们文件中时,他的文件A的副本会被用某种方式标记成冲突状态:他可以看到两个互相冲突的修改,从而手工做出选择。注意,软件无法自动解决冲突,只有人可以理解并做必要的、智能的选择。只要Harry手动解决了这些重叠的修改--可能在和Sally讨论后--他就可以安全的把合并后的文件保存回资料库了。

Bbs.Svn8.Com


拷贝-修改-合并模型听起来有点混乱,但在实践中,它工作的非常稳定。用户们可以并行工作,从来用不着等别人。当他们在同一些文件上工作时,实践表明大部分同时做的修改根本不会互相重叠,冲突不经常发生。而且花费在解决冲突上的时间比锁定系统所浪费的时间少的多。 Svn中文网

最后,这些问题都可以归结到一个关键因素:用户沟通。如果用户们沟通不好,语义和语法上的冲突都会增加。没有那个系统能强制用户完美的沟通,没有那个系统能检测语义上的冲突。所以,不要被这样的虚假承诺蒙蔽:加锁系统可以在某种程度上防止冲突。实际上,看起来加锁比别的系统更制约生产力。 Bbs.Svn8.Com

本文来自Svn中文网[www.svn8.com]转发请保留本站地址:http://www.svn8.com/svnsy/20080202/11.html


========
         Subversion实战
本文来自Svn中文网[www.svn8.com]转发请保留本站地址:
http://www.svn8.com/svnsy/20080202/12.html

是时候从抽象回到具体了。这一节,我们将演示Subversion的使用实例。

Bbs.Svn8.Com

工作副本你已经对工作副本有了些了解,现在我们要演示如何用Subversion客户程序创建和使用工作副本。 Www.Svn8.Com

一个Subversion的工作副本是你本地系统上的一个普通的目录树,包含一系列文件。客户随他所愿来编辑这些文件, 如果他们是源码文件,你可以用通常的方法来编译程序。你的工作副本是你的私人工作区。Subversion永远不会自行加入别人的改动,或把你的改动给别人,除非你明确的让它这么做。

Bbs.Svn8.Com


在你对你的工作副本中的一些文件作了改动,并且验证了它们工作正常后,Subversion提供给你命令来把你的改动“发布”给其他和你一起为你的项目工作的人(通过写到资料库中)。如果别人发布了他们的修改,Subversion也提供命令给你来把这些改动合并到你的工作目录(通过从资料库读取)。

参考资料:www.svn8.com

工作副本也包含有一些由Subversion创建和维护的额外文件,Subversion利用这些文件来完成命令。具体点说,你的工作副本中的每个目录包含一个名字为.svn的子目录,也被称为工作副本管理目录。管理目录中的文件帮助Subversion识别那些文件包含未发布的修改,那些文件相对于别人的工作已经过时了。 Svn中文网

一个典型的Subversion资料库常会保存多个项目的文件(或源码)。通常,在资料库的目录树中每个项目都是一个子目录。按这种按排,一个用户的工作目录通常对应于资料库中一个特定的子树。

Bbs.Svn8.Com


例如,假如你有一个资料库,其中有两个软件项目,paint和calc。每个项目都位于自己的顶级子目录下,如图 2.6 “资料库的文件系统”所示。

Svn8.Com


图 2.6. 资料库的文件系统
Www.Svn8.Com


要得到一个工作副本,你必须检出资料库的某个子树(名词“检出”可能听起来有点像锁定或保留资源,其实不然,它仅仅是为你创建了这个项目的私有拷贝)。例如, 如果你检出/calc,你将得到一个如下的工作副本: Svn中文网

$ svn checkout http://svn.example.com/repos/calc
A  calc
A  calc/Makefile
A  calc/integer.c
A  calc/button.c

$ ls -A calc
Makefile  integer.c  button.c  .svn/
 Bbs.Svn8.Com 那一列A说明Subversion增加了一些条目到你的工作副本。现在你有了资料库中/calc目录的一个副本,和一个附加.svn子目录--它保存Subversion需要的额外信息,像前面提到的那样。 Svn8.Com

资料库URL Www.Svn8.Com
Subversion资料库可以通过多种方法来访问--在本地盘,或通过不同的网络协议。然而,一个资料库位置总是一个URL,表2-1描述了 不同的URL模式如何对应于不同的访问方法。 Svn中文网

表 2.1. 表2.1资料库访问URL 参考资料:www.svn8.com
模式 访问方法
file:/// 直接访问(在本地盘上)
http:// 通过WebDav协议访问支持Subversion的Apache服务器
https:// 和http://一样,不过加了SSL加密
svn:// 通过特有协议访问 svnserve服务器
svn+ssh:// 和svn://一样,但通过SSH通道

大部分的SubversionURL使用标准的语法, 可以在URL中指定服务器名和端口号。记住, file:访问方法只对本地资料库有效--实际上,为了与遵循惯例,这种URL中的服务器名要求为空或者是 localhost:

Svn中文网


$ svn checkout file:///path/to/repos

$ svn checkout
file://localhost/path/to/repos

 Svn中文网 另外,在Windows平台上使用file:模式的用户,要访问位于同一机器上但不和客户程序当前工作驱动器相同的驱动器上的的资料库,需要使用一种非官方的 “标准”语法。以下两种URL路径语法都可以,这里X表示资料库所在驱动器。 Svn中文网

C:/> svn checkout file:///X:/path/to/repos

C:/> svn checkout "
file:///X|/path/to/repos"

 Svn8.Com 在第二种语法中,你需要对URL加引号,以使竖线不被解释成管道。

Bbs.Svn8.Com


注意,URL使用正斜杠,虽然在windows上的本地路径使用反斜杠。

参考资料:www.svn8.com

假设你对button.c作了修改。由于.svn目录记住了文件的修改日期和原料的内容,所以Subversion能辨别出你修改了文件。然而,Subversion不会公布你的修改,除非你明确让它这么做。发布你的修改这一行为,一般称为提交(或检入)修改到资料库。

Www.Svn8.Com

要把你的修改发布给别人,你要使用Subversion的commit命令: 参考资料:www.svn8.com

$ svn commit button.c
Sending        button.c
Transmitting file data .
Committed revision 57.
 
Www.Svn8.Com 现在你对button.c的修改已经被提交到资料库,如果其他用户检出/calc的一个工作副本,他们将在最近的文件版本中看到你的修改 。 Www.Svn8.Com

假设你有一个合作者,Sally,她和你同时检出了/calc的一个工作副本。当你提交你对 button.c的修改到资料库时,Sally的工作副本并没有被修改。Subversion只会在用户的要求下修改工作副本。

Www.Svn8.Com

要让她的项目跟上,Sally要让Subversion来更新他的工作副本,这需要Subversion的update命令。这个命令会把你的修改合并到她的工作副本,还有其他在她检出后的修改。

Svn中文网

$ pwd
/home/sally/calc

$ ls -A
.svn/ Makefile integer.c button.c

$ svn update
U button.c
 Svn8.Com svn update命令的输出说明Subversion更新了 button.c的内容。注意Sally不需要指明要更新那些文件。Subversion利用.svn目录和资料库中的信息来决定那些文件需要被更新。 参考资料:www.svn8.com

修订版(Revision)一次svn commit操作能把对任意个数的文件和目录作的所有改动以一个原子事务发布。在你的工作副本里,你可以改变文件内容,创建,删除,重命名和复制文件和目录,然后把所有这些修改作为一个单元提交。

Www.Svn8.Com


在资料库中,每次提交都被看作一个原子事务:要么所有的提交修改发生,要么全不发生。Subversion在碰到程序崩溃,系统崩溃,网络问题和其他用户的动作时也会努力维持原子性。

Svn8.Com


资料库在每次接到一次提交请求时,会创建一个文件树的新状态,称为一个修订版(revision)。每一个修订版都被赋予一个唯一的自然数,比上一个修订版大一。对新创建的资料库,初始的修订版被编号为0,这个修订版仅仅是一个空的根目录,没有任何内容。 Svn8.Com

图 2.7 “资料库”展示了一个形象化的看待资料库的好办法。想象一个修订版号码的数列,从0开始,从左到右延伸。每个修订版号码有一个文件树挂在下面,每个文件树都是一次提交后的资料库的一个“快照”。 Bbs.Svn8.Com

图 2.7. 资料库
Bbs.Svn8.Com

 

全局的修订版号码 Svn8.Com
和其他很多版本控制系统不同,Subversion的修订版作用于整个树,而不是单个文件。每个修订版号码指定了一个完整的树,是资料库在一些提交完成后的一个特定的状态。另一种看待它的办法是,修订版号码N代表资料库系统在N次提交后的状态。当一个Subversion用户说到 “foo.c的修订版5”时,他的实际意义是 “foo.c在修订版5中存在。” 注意,一般来说,一个文件修订版N和M不一定要不同。因为CVS使用单文件修订版号码,CVS用户应该看看针对CVS用户写的Subversion说明,那里提供了更详细的信息。

Svn8.Com

重要的是要注意到,工作副本并不总是对应于资料库中某个单独的修订版;他可能包含来自不同修订版的文件。例如,假设你检出了一个最新修订版是4的工作副本:

Bbs.Svn8.Com


calc/Makefile:4
     integer.c:4
     button.c:4
 Svn8.Com 这时,这个工作目录和资料库中的修订版4精确对应。然而,假如你对button.c作了修改并提交了。假设没有别的提交发生,你的提交将在资料库中创建修订版5,而你的工作副本看起来会是这样: Svn8.Com

calc/Makefile:4
     integer.c:4
     button.c:5
 Bbs.Svn8.Com 设想,在这时Sally提交了她对 integer.c的修改,创建了修订版6。如果你用svn update命令更新你的工作区,它看起来会是这样: Bbs.Svn8.Com

calc/Makefile:6
     integer.c:6
     button.c:6
 Svn8.Com Sally对integer.c的修改将出现在你的工作副本里,而你的修改还在button.c里,在这个例子里,Makefile得内容在修订版4.5.6中都是一样的,但是Subversoin会把你工作副本中的Makefile with revision 6 to 标记为修订版6,以表明它仍然是最新的。因此,在你对工作副本做了一个完整的更新后,它会仍然精确的对应于资料库中的一个修订版。

Svn中文网


工作副本如何跟踪资料库对工作副本中的每一个文件,Subversion在 .svn/管理区中记录了两方面必要的信息: 参考资料:www.svn8.com

你的工作副本基于那一个修订版(称为这个文件的工作修订版),以及 参考资料:www.svn8.com

一个时间戳,用来记录本地副本被资料库更新的最后时间。 Www.Svn8.Com

有了这些信息,靠和资料库交互,Subversion能分辨一个工作文件处在下面四个状态中的那个: Svn8.Com

未修改,是最新的
在工作副本中这个文件没被修改,从它的工作修订版以来还没有修改提交到资料库。对这个文件作svn commit,什么都不会发生。对这个文件作svn update也什么都不会发生。

Bbs.Svn8.Com


在本地修改了,是最新的
这个文件在工作目录里已经被修改了,但从它的工作修订版以来还没有新修改提交到资料库。本地有尚未提交到资料库的修改,因而对这个文件作svn commit,会把你的修改成功的发布,对这个文件作svn update什么都不会发生。

Www.Svn8.Com

未修改,已经过时了
在工作副本中这个文件没被修改,但在资料库它已经被修改了。最终它应该被更新,以使它和公共修订版保持同步。对这个文件作svn commit,什么都不会发生。对这个文件作 svn update将把最新的修改调入你的工作副本。 参考资料:www.svn8.com

在本地修改了,已经过时了
这个文件在工作目录和资料库中都已经被修改了。对这个文件作svn commit,会由于 “文件已过时”而失败。这个文件应该首先被更新,对这个文件作svn update,会首先尝试把公共的修改合并到本地的修改中。如果Subversion无法比较合理的自动完成合并,它会把冲突留给用户来解决。

参考资料:www.svn8.com

听起来这种方式好像有很多东西要跟踪,但是 svn status 命令能给你展示你工作副本中任何条目的状态。关于这个命令的更多信息,参见“svn status”一节。 Bbs.Svn8.Com

混合修订版的局限作用一个基本原则,Subversion尽可能做到灵活。一个特别的灵活性是工作副本可以包含混合的修订版号。

Bbs.Svn8.Com

首先,为什么这种灵活性要被看作是特性而不是负担的原因可能不那么明显。在完成对资料库的一次提交后,新提交的文件和目录比工作副本里的其他文件处于更新的工作修订版。这看起来有点乱。像前面演示的那样,工作副本总可以运行 svn update命令来使自己只有一个工作修订版。为什么有些人故意想要混合的工作修订版? Svn中文网

如果你的项目足够复杂,你会发现有时强制 “回溯”你的部分的工作副本是很有用的;你将在第三章学会如何做。可能你想测试一个字模块的一个较早的版本,这个子模块包含在一个子目录里,或者可能你想在最新文件树的环境下检查一个文件的一系列先前的版本。 Svn8.Com

不管你如何利用你工作副本中的混合修订版,这个灵活性都有一些局限。

Svn8.Com


首先,如果一个文件或目录不是完全最新的话,你没法提交对它们的删除。如果资料库中存在一个这个文件的新版本,你删除的企图会被驳回,以免意外毁掉了你还没有看到的修改。 Bbs.Svn8.Com

其次,如果一个目录不是最新的,你无法提交对它的元数据的修改。在第六章,你将学到给一个条目附加 “属性”。一个目录的工作修订版定义了一个特殊的条目和属性集合, 因而,提交对一个过时目录的属性修改可能破坏你还没看到的属性。

本文来自Svn中文网[www.svn8.com]转发请保留本站地址:http://www.svn8.com/svnsy/20080202/12.html

==========
    总结
在这一章我们已经涉及了很多基本的Subversion概念:
Www.Svn8.Com

我们介绍了中央资料库,客户工作副本和资料库修订版树队列的概念。

Svn8.Com

我们看到了一些简单的例子,使用“拷贝-修改-合并” 模型,两个合作者如何使用Subversion来互相发布和接受对方的修改。 Bbs.Svn8.Com

我们讲了一点Subversion在工作副本中跟踪和管理信息的机制 Svn中文网

到这里,你应该对Subversion如何工作有一个总体上的不错的了解了。有了这些知识,现在你应该准备好投入到下一章了,这一章是对Subversion的命令和特性的详细地导引

本文来自Svn中文网[www.svn8.com]转发请保留本站地址:http://www.svn8.com/svnsy/20080202/13.html

原创粉丝点击