Pro Git 4.1 通訊協定

出自DILA Wiki

Git 可以使用四種主要的協定來傳輸資料:本地傳輸、SSH 協定、Git 協定和 HTTP 協定。下面分別介紹一下他們以及你應該(或不應該)在怎樣的情形下使用他們。

值得注意的是除了 HTTP 協定之外,其他所有協定都要求在伺服器端安裝並運行 Git 。

本地協定

最基礎的就是 本地協議(Local protocol) 了,遠端倉庫在該協定中就是硬碟上的另一個目錄。這常見於團隊每一個成員都對一個共用的檔案系統(例如 NFS)擁有訪問權,抑或比較少見的是每個人都登入到同一台電腦的時候。後者不是很理想,因為你所有的代碼倉庫實例都儲存在同一台電腦裡,增加了災難性資料損失的可能性。

如果你使用一個共用的檔案系統,就可以在一個本地倉庫裡克隆,推送和獲取。要從這樣的倉庫裡克隆或者將其作為遠端倉庫添加到現存的專案裡,可以用指向該倉庫的路徑作為URL。比如,克隆一個本地倉庫,可以用如下命令完成:

$ git clone /opt/git/project.git

或者這樣:

$ git clone file:///opt/git/project.git

如果你在URL的開頭明確的使用 file:// ,那麼 Git 會以一種略微不同的方式運行。如果你只給出路徑,Git 會嘗試使用硬連結或者直接複製它需要的檔。如果使用了 file:// ,Git會調用它平時通過網路來傳輸資料的工序,而這種方式的效率相對很低。使用 file:// 首碼的主要原因是當你需要一個不包含無關引用或物件的乾淨倉庫副本的時候——一般是從其他版本控制系統的導入之後或者類似的情形(參見第9章的維護任務)。我們這裡使用普通路徑,因為通常這樣總是更快。

要添加一個本地倉庫到現有 Git 專案,執行如下命令:

$ git remote add local_proj /opt/git/project.git

然後就可以像在網路上一樣向這個遠端倉庫推送和獲取資料了。

優點

以檔案為基礎的倉庫(file-based repositories)的優點在於它的簡單,同時保留了現存檔的許可權和網路存取權限。如果你的團隊已經有一個全體共用的檔案系統,建立倉庫就十分容易了。你只需把一份純倉庫的副本放在大家能訪問的地方,然後像對其他共用目錄一樣設置讀寫許可權就可以了。我們將在下一節「在伺服器上部署 Git」中討論如何為此匯出一個純倉庫的副本。

這也是個從別人工作目錄裡獲取他工作成果的快捷方法。假如你和你的同事在一個專案中合作,他們想讓你檢出(check out)一些東西的時候,運行類似 git pull /home/john/project 通常會比他們推送到伺服器,而你又從伺服器獲取簡單得多。

缺點

這種方法的缺點是,與基本的網路連接訪問相比,能從不同的位置訪問的共用許可權難以架設。如果你想從家裡的筆記型電腦上推送,就要先掛載遠端硬碟,這和基於網路連接的訪問相比更加困難和緩慢。

另一個很重要的問題是該方法不一定就是最快的,尤其是對於共用掛載的檔案系統。本地倉庫只有在你對資料存取速度快的時候才快。在同一個伺服器上,如果二者同時允許 Git 訪問本地硬碟,通過 NFS 訪問倉庫通常會比 SSH 慢。

SSH 協議

Git 使用的傳輸協議中最常見的可能就是 SSH 了。這是因為大多數環境已經支持通過 SSH 對伺服器的訪問——即使還沒有,也很容易架設。SSH 也是唯一一個同時便於讀寫操作的網路通訊協定。另外兩個網路通訊協定(HTTP 和 Git)通常都是唯讀的,所以雖然二者對大多數人都可用,但執行寫操作時還是需要 SSH。SSH 同時也是一個驗證授權的網路通訊協定;而因為其普遍性,通常也很容易架設和使用。

通過 SSH 克隆一個 Git 倉庫,你可以像下面這樣給出 ssh:// 的 URL:

$ git clone ssh://user@server:project.git

或者不指明某個協定——這時 Git 會預設使用 SSH :

$ git clone user@server:project.git

也可以不指明用戶,Git 會預設使用你當前登錄的用戶。

優點

使用 SSH 的好處有很多。首先,如果你想擁有對網路倉庫的寫入許可權,基本上不可能不使用 SSH。其次,SSH 架設相對比較簡單—— SSH daemons 很常見,很多網路系統管理員都有一些使用經驗,而且很多作業系統都已經內建,或者提供相關的管理工具。再次,通過 SSH 進行存取是安全的——所有資料傳輸都是加密和授權的。最後,類似 Git 和 本地協議,SSH 很有效率,它會在傳輸之前盡可能的壓縮資料。

缺點

SSH 的限制在於你不能通過它實現倉庫的匿名存取。即使僅為讀取資料,人們也必須在能通過 SSH 訪問主機的前提下才能使用倉庫,這使得 SSH 不利於開源的專案。如果你僅僅在公司網路裡使用,SSH 可能是你唯一需要使用的協定。如果想允許對專案的匿名唯讀訪問,那麼除了為自己推送而架設 SSH 協定之外,還需要其他協定來讓別人獲取資料。

Git 協議

接下來是 Git 協議。這是一個包含在 Git 套裝軟體中的特殊守護進程(daemon);它會監聽一個提供類似於 SSH 服務的特定埠(9418),而無需任何授權。用 Git 協定營運倉庫,你需要創建 git-export-daemon-ok 檔——它是協定進程提供倉庫服務的必要條件——但除此之外該服務沒有什麼安全措施。要麼所有人都能克隆 Git 倉庫,要麼誰也不能。這也意味著該協議通常不能用來進行推送。你可以允許推送操作;然而由於沒有授權機制,一旦允許該操作,網路上任何一個知道專案 URL 的人將都有推送許可權。不用說,這是十分罕見的情況。

優點

Git 協定是現存最快的傳輸協議。如果你在提供一個有很大訪問量的公共專案,或者一個不需要對讀操作進行授權的龐大項目,架設一個 Git 守護進程來供應倉庫是個不錯的選擇。它使用與 SSH 協定相同的資料傳輸機制,但省去了加密和授權的開銷。

缺點

Git 協議不利的一面是缺少授權機制。用 Git 協議作為訪問專案的唯一方法通常是不可取的。一般做法是,同時提供 SSH 介面,讓幾個開發者擁有推送(寫)許可權,其他人通過 git:// 擁有唯讀許可權。 Git 協定可能也是最難架設的協議。它要求有單獨的守護進程,需要定制——我們將在本章的「Gitosis」一節詳細介紹它的架設——需要設定 xinetd 或類似的程式,而這些就沒那麼平易近人了。該協議還要求防火牆開放 9418 埠,而企業級防火牆一般不允許對這個非標準埠的訪問。大型企業級防火牆通常會封鎖這個少見的埠。

HTTP/S 協議

最後還有 HTTP 協議。HTTP 或 HTTPS 協議的優美之處在於架設的簡便性。基本上,只需要把 Git 的純倉庫檔(bare Git repository)放在 HTTP 的檔根目錄下,配置一個特定的 post-update 掛鉤(hook),就搞定了(Git 掛鉤的細節見第七章)。從此,每個能訪問 Git 倉庫所在伺服器上的 web 服務的人都可以進行克隆操作。下面的操作可以允許通過 HTTP 對倉庫進行讀取:

$ cd /var/www/htdocs/
$ git clone --bare /path/to/git_project gitproject.git
$ cd gitproject.git
$ mv hooks/post-update.sample hooks/post-update
$ chmod a+x hooks/post-update

這樣就可以了。Git 附帶的 post-update 掛鉤會預設執行合適的命令(git update-server-info)來確保通過 HTTP 的獲取和克隆正常工作。這條命令在你用 SSH 向倉庫推送內容時運行;之後,其他人就可以用下面的命令來克隆倉庫:

$ git clone http://example.com/gitproject.git

在本例中,我們使用了 Apache 設定中常用的 /var/www/htdocs 路徑,不過你可以使用任何靜態 web 服務——把純倉庫放在它的目錄裡就行了。Git 的資料是以最基本的靜態檔的形式提供的(關於如何提供檔的詳情見第9章)。

通過HTTP進行推送操作也是可能的,不過這種做法不太常見並且牽扯到複雜的 WebDAV 設定。由於很少用到,本書將略過對該內容的討論。如果對 HTTP 推送協議感興趣,不妨在這個位址看一下操作方法:http://www.kernel.org/pub/software/scm/git/docs/howto/setup-git-server-over-http.txt 。通過 HTTP 推送的好處之一是你可以使用任何 WebDAV 伺服器,不需要為 Git 設定特殊環境;所以如果主機提供商支援通過 WebDAV 更新網站內容,你也可以使用這項功能。

優點

使用 HTTP 協定的好處是易於架設。幾條必要的命令就可以讓全世界讀取到倉庫的內容。花費不過幾分鐘。HTTP 協議不會佔用過多伺服器資源。因為它一般只用到靜態的 HTTP 服務提供所有的資料,普通的 Apache 伺服器平均每秒能供應數千個檔——哪怕是讓一個小型的伺服器超載都很難。

你也可以通過 HTTPS 提供唯讀的倉庫,這意味著你可以加密傳輸內容;你甚至可以要求用戶端使用特定簽名的 SSL 證書。一般情況下,如果到了這一步,使用 SSH 公共金鑰可能是更簡單的方案;不過也存在一些特殊情況,這時通過 HTTPS 使用帶簽名的 SSL 證書或者其他基於 HTTP 的唯讀連接授權方式是更好的解決方案。

HTTP 還有個額外的好處:HTTP 是一個如此常見的協議,以至於企業級防火牆通常都允許其埠的通信。

缺點

HTTP 協議的缺點在於,相對來說用戶端效率更低。克隆或者下載倉庫內容可能會花費更多時間,而且 HTTP 傳輸的體積和網路開銷比其他任何一個協議都大。因為它不能聰明的只提供你所需的資料——傳輸過程中沒有服務端的動態計算——因而 HTTP 協定經常會被稱為 傻瓜(dumb) 協議。更多 HTTP 協定和其他協定效率上的差異見第九章。