以前在一臺vps服務器上面搭建了Git服務器,用來作代碼管理,方便團隊開發。可是問題也就相應的來了,使用git能夠輕鬆的上傳代碼,而因爲作的是web開發,每次還都獲得服務器上把代碼手動pull或者複製到網頁所在的文件夾下,也就比較麻煩,不適合我這種懶人。git提供了hook機制,能夠很容易的實現代碼的自動部署。nginx
我的原創,版權全部,轉載請註明原文出處:git
http://www.embbnux.com/2014/09/05/git_server_let_code_auto_deploy/web
一 git機制簡要介紹瀏覽器
git使用的是代碼倉庫,git服務端有倉庫,稱爲遠端倉庫,咱們clone下來的,本地也有一個倉庫稱爲本地倉庫。咱們commit的時候是把代碼提交到了本地倉庫,push時,是把代碼提交到了遠端倉庫。pull的時候是把代碼從遠端倉庫下載到本地倉庫。服務器
代碼倉庫對代碼的存儲使用了版本指針,每一個提交的版本都對應一個HEAD指針,當前版本指針隨着代碼的提交而一直改變。post
二 自動部署原理fetch
說說如今代碼的分佈狀況,開發者電腦上的本地倉庫,git服務器上的遠端倉庫,web服務器上的另外一個本地倉庫,咱們瀏覽器訪問的就是這裏的代碼。spa
要實現自動部署,就是要當開發者從本地倉庫提交代碼到遠端倉庫的時候,自動把代碼部署到web服務器的本地倉庫,實現開發者本地倉庫和web服務器的本地倉庫的同步。.net
三 實現自動部署指針
按照上面說的,就是要在開發者提交的時候,自動觸發腳本,腳本去實現web端代碼的部署.
這裏就得講一下git的hook機制,當git服務器接到各類事件時觸發,這裏使用的hook是
post-receive
這個hook在git服務器受到push請求,而且接受完代碼提交時觸發。
具體代碼體現:
在git遠端倉庫的hooks目錄下新建post-receive文件:
#!/bin/sh #author: embbnux #Blog of Embbnux: http://www.embbnux.com #判斷是否是遠端倉庫 IS_BARE=$(git rev-parse --is-bare-repository) if [ -z "$IS_BARE" ]; then echo >&2 "fatal: post-receive: IS_NOT_BARE" exit 1 fi unset GIT_DIR DeployPath="/var/web" echo "===============================================" cd $DeployPath echo "deploying the test web" #git stash #git pull origin master git fetch --all git reset --hard origin/master time=`date` echo "web server pull at webserver at time: $time." echo "================================================"
保存後賦予可執行權限:
1
chmod
+x hooks
/post-receive
這樣在開發者提交代碼的時候,就會自動部署。
在這裏補充說明下: 由於我創建git倉庫時用的是git用戶 可是在自動部署時站點服務器採用的是nginx服務器的 git用戶屬於git組 nginx屬於nginx組 因此在這裏就是把post-receive設置成nginx組 若是不設置的話在站點目錄下是沒有辦法更新文件的(會提示沒有權限操做)
自動部署的時候,我這裏使用的是git fetch,也可使用git pull實現,這裏兩個的區別主要是pull事先fetch後而後再用merge,來合併本地和遠端的代碼。可是有個問題,若是開發者在提交過程出現失誤,使用git reset復位後,如今遠端的代碼版本低於web端的代碼版本,再使用pull的時候就不能實現和開發者本地的代碼的同步。因此這裏使用fetch後,在強制使用reset實現web端的代碼版本指針和git服務端的一致。因爲沒有使用merge,因此之後web端的代碼就不能在服務器上直接更改了,對web端代碼的各類改變都應該使用開發者電腦進行代碼提交,否則會報錯。