標籤

另一個常見的版本控制系統概念是標­¾(tag),一個標籤只是一個項目某一時間的「快照」,在Subversion裡這個概念無處不在—每一次提交的修訂版本都是一個精確的快照。

然而人們希望更人性化的標籤名稱,像release-1.0。他們也希望可以對一個子目錄快照,畢竟,記住release-1.0是修訂版本4822的某一小部分不是件很容易的事。

建立簡單標籤

svn copy再次登場,你希望建立一個/calc/trunk的一個快照,就像HEAD修訂版本,建立這樣一個拷貝:

$ svn copy http://svn.example.com/repos/calc/trunk \
           http://svn.example.com/repos/calc/tags/release-1.0 \
      -m "Tagging the 1.0 release of the 'calc' project."

Committed revision 351.

這個例子假定/calc/tags目錄已經存在(如果不是,可以使用svn mkdir建立。),拷貝完成之後,一個表示當時HEAD版本的/calc/trunk目錄的鏡像已經永久的拷貝到release-1.0目錄。當然,你會希望更精確一點,以防其他人在你不注意的時候提交修改,所以,如果你知道/calc/trunk的版本350是你想要的快照,你可以使用svn copy加參數 -r 350

但是等一下:標籤的產生過程與建立分支是一樣的?是的,實際上在Subversion中標籤與分支沒有區別,都是普通的目錄,通過copy命令得到,與分支一樣,一個目錄之所以是標籤只是人們決定這樣使用它,只要沒有人提交這個目錄,它永遠是一個快照,但如果人們開始提交,它就變成了分支。

如果你管理一個版本庫,你有兩種方式管理標籤,第一種方法是禁止命令:作為項目的政策,我們要決定標籤所在的位置,確定所有用戶知道如何處理拷貝的目錄(也就是確保他們不會提交他們),第二種方法看來很過分:使用訪問控制腳本來阻止任何想對標籤目錄做的非拷貝的操作(見第 6 章 服務設定)這種方法通常是不必要的,如果一個人不小心提交了到標籤目錄一個修改,你可以簡單的取消,畢竟這是版本控制啊。

建立複雜標籤

有時候你希望你的「快照」能夠很複雜,而不只是一個單獨修訂版本的一個單獨目錄。

舉個例子,假定你的項目比我們的的例子calc大的多:假設它保存了一組子目錄和許多文件,在你工作時,你或許決定建立一個包括特定特性和Bug修正的工作副本,你可以通過選擇性的回溯文件和目錄到特定修訂版本(使用svn update -r)來實現,或者轉換文件和目錄到特定分支(使用svn switch),這樣做之後,你的工作副本成為版本庫不同版本和分支的司令部,但是經過測試,你會知道這是你需要的一種精確資料組合。

是時候進行快照了,拷貝URL在這裡不能工作,在這個例子裡,你希望把本地拷貝的部署做鏡像並且保存到版本庫中,幸運的是,svn copy包括四種不同的使用方式(在第 9 章 Subversion 完全參考可以詳細閱讀),包括拷貝工作副本到版本庫:

$ ls
my-working-copy/

$ svn copy my-working-copy http://svn.example.com/repos/calc/tags/mytag

Committed revision 352.

現在在版本庫有一個新的目錄/calc/tags/mytag,這是你的本地拷貝的一個快照—混合了修訂版本,URL等等。

一些人也發現這一特性一些有趣的使用方式,有些時候本地拷貝有一組本地修改,你希望你的協作者看到這些,不使用svn diff並發送一個補定文件(不會捕捉到目錄、符號鏈和屬性的修改),而是使用svn copy來「上傳」你的工作副本到一個版本庫的私有區域,你的協作者可以選擇完整的取出你的工作副本,或使用svn merge來接受你的精確修改。

雖然這是上傳快速工作副本快照的一個好方法,但這不是初始建立分支的好方法。分支建立必須是它本身的事件,而這個方法建立的分支包含了額外修改,都包含在一個單獨修訂版本裡。這讓我們很難識別分支點的單個修訂版本號碼。

提示

你是否發現你做出了複雜的修改(在/trunk的工作副本),並突然發現,「這些修改必須在它們自己的分支?」處理這個問題的技術可以總結為兩步:

$ svn copy http://svn.example.com/repos/calc/trunk \
           http://svn.example.com/repos/calc/branches/newbranch
Committed revision 353.

$ svn switch http://svn.example.com/repos/calc/branches/newbranch
At revision 353.

就像svn update命令,svn switch會保留工作副本的本地修改,此刻,你的工作副本反映到新建的分支上,而你的下一次svn commit會發送修改到伺服器。