第1章 SVN服務實戰應用指南
1.1 SVN介紹
1.1.1 什么是SVN(Subversion)?
- Svn(subversion)是近年來崛起的非常優秀的版本管理工具,與CVS管理工具一樣,SVN是一個跨平台的開源的版本控制系統。Svn版本管理工具管理着隨時間改變的各種數據。這些數據放置在一個中央資料檔案庫(repository)中,這個檔案庫很像一個普通的文件服務器或者FTP服務器,但是,與其他服務器不同的是,SVN會備份並記錄每個文件每一次的修改更新變動。這樣我們就可以把任意一個時間點的檔案恢復到想要的某一個舊的版本,當然也可以直接瀏覽指定文件的更新歷史記錄。
- 為什么會有svn這樣一個項目?
- 官方解釋:為了接管CVS的用戶基礎,確切的說,我們寫了一個新的版本控制系統,它和CVS很相似,但是它修正了以前CVS所沒有解決的許多問題。問題見SVN官方首頁。
- SVN是一個非常通用的軟件系統,它常被用來管理程序源碼,但是它也可以管理任何類型的文件,如文本,視頻,圖片等等。
SVN相關站點:
Subversion官網:
http://subversion.tigris.org/
http://subversion.apache.org/
svn客戶端:http://toroisesvn.net/
svn中文網站:http://www.iusesvn.com/
中文常見問題解答FAQ:http://subversion.apache.org/faq.zh.html
官方手冊:http://svnbook.red-bean.com/ 中英都有
1.2 svn與git的區別
1.2.1 svn集中式版本控制系統
svn版本控制系統是集中式的數據管理,存在一個中央版本庫,所有開發人員本地開發所使用的代碼都是來自於這個版本庫,提交代碼也都必須提交到這個中央版本庫。
svn版本控制系統工作流程如下:
在中央庫上創建或從主干復制一個分支
從中央庫check out 下這個分支的代碼
增加自己的代碼文件,修改現存的代碼或刪除代碼文件
commit(提交)代碼,假設有人在剛剛的分支上提交了代碼,你就會被提示代碼過期,你得先up你的代碼后再提交。up代碼的時候如果出現沖突,需要解決好沖突后再進行提交。
缺點
當無法連接到中央版本庫的環境下,你無法提交代碼,將代碼加入版本控制;
你無法查看代碼的歷史版本以及版本的變化過程。提交到版本控制系統中的代碼我們都默認通過自測可運行的,如果某個模塊的代碼比較復雜,不能短時間內實現為可測試的功能,那么你需要等很長的時間才能提交自己的代碼,由於代碼庫集中管理,因此,需要對中央版本庫的存儲做備份。這點分布式的版本控制系統要好一些。Svn的備份要備份所有代碼數據以及所有更改的版本記錄。
1.2.2 git分布式的版本控制
- git是由Linus開發的,所以很自然的git和Linux文件系統結合的比較緊密,以至於在windows上你必須使用cygwin才能使其完美的工作。
- 那git憑啥叫做分布式的版本控制系統呢?還是從其工作模式講起把。
- git中沒有了中央版本庫的說法了,但是為了開發小組的代碼共享,我們通常還是會搭建一個遠程的git倉庫。
- 但是和svn不同的是,開發者本地也包含了一個完整的git倉庫,從某種程度上說本地的倉庫和遠程的倉庫在身份上是等價的,沒有主從之分。
如果你的項目是閉源項目,或者你習慣於以往的集中式的管理模式的話,那么在git下你也可以像svn那樣的工作,只是流程中可能會增加一些步驟。
你本地創建一個git庫,並將其add到遠程git庫中。
你在本地添加或者刪除文件,然后commit,當然commit操作都是提交到本地的git庫中了。(嗯,其實是提交到git目錄下的objects目錄中去了)
將本地git庫的分支push到遠程git庫的分支,如果這個時候遠程git庫中已經有別人push過,那么遠程git庫將不允許你push,這時候你需要先pull,然后如果有沖突,處理好沖突,commit到本地git庫后,再push到遠程git庫。
從上面的描述我們可以看到,我們每個開發人員的本地都會有一個git庫,我們可以隨時進行commit而不需要聯網,可以隨時查看歷史版本,當某一個功能點開發完了之后我們可以將commit后的內容push到遠程git庫了,如果遠程git庫的版本在你上次clone或者pull之后變化了,那么你需要進行pull並處理沖突,提交之后,再push到遠程git庫。
1.3 企業應用場景
svn仍是當前企業的主流。git正在發展,也許未來也會成為主流,但現在還不是。如果有精力,能同時掌握更好。
1.4 運維人員掌握版本管理
對於版本管理系統,運維人員需要掌握的技術點
安裝,部署,維護,排障。
簡單使用,很多公司都是由開發來管理,包括建立新倉庫和添加刪除賬號
對於版本控制系統,運維人員相當於開發商,開發人員是業主,運維搭建的系統為開發人員服務的。
1.5 SVN服務運行模式與訪問方式
1.5.1 SVN服務端運行方式
svn服務常見的運行訪問方式有3種:
(1)獨立服務器訪問
訪問地址如:svn://svn.yunjisuan.org/sadoc;
(2)借助apache等http服務
訪問地址如:http://svn.yunjisuan.com/sadoc;
a,單獨安裝apache+svn(不要用)
b,CSVN(apache+svn)是一個單獨的整合的軟件,帶web界面管理的SVN軟件
(3)本地直接訪問(例如:file://application/svndata/sadoc)

在這里,主要介紹第一種方式以及第二種方式中的CSVN web管理方式
1.5.2 SVN客戶端訪問方式
SVN客戶端可以通過多種方式訪問服務器端,例如:本地磁盤訪問,或各種各樣不同的網絡協議訪問,但一個版本庫地址永遠都是一個URL,URL反映了訪問方法。

1.6 SVN檔案庫數據格式
svn存儲版本數據有2種方式:BDB(一種事務安全型表類型)和FSFS(一種不需要數據庫的存儲系統)。因為BDB方式在服務器中斷時,有可能鎖住數據,所以還是FSFS方式更安全一點。
-
BDB:
伯克利DB(Berkeley DB),版本庫可以使用的一種經過充分測試的后台數據庫實現,不能在通過網絡共享的文件系統上使用,伯克利DB是Subversion 1.2版本以前的缺省版本庫格式
-
FSFS:
一個專用於Subversion版本庫的文件系統后端,可以使用網絡文件系統(例如 NFS 或 SMBFS)。是1.2版本及其后的缺省版本庫格式。
1.7.1 SVN 集中式版本管理系統
Svn是一種集中式文件版本管理系統。集中式管理的工作流程如下圖:

集中式代碼管理的核心是SVN服務器,所有開發者在開始新一天的工作之前必須從服務器獲取代碼,然后進行開發,最后解決沖突,提交。所有的版本信息都放在SVN服務器上。因此如果脫離了服務器,開發者就無法進行提交代碼工作。
1.7.2 開發者利用SVN版本管理系統工作過程
下面舉例說明:
開始新一天的工作:
首先從SVN服務器下載項目組最新代碼。
進入自己的分支,進行開發工作,每隔一小時向服務器上自己的分支提交一次代碼(很多程序員都有這個習慣。因為有時候自己對代碼改來改去,最后又想還原到新一個小時的版本,或者看看前一個小時自己修改了哪些代碼,就需要這樣做了)。
下班時間快到了,把自己的分支合並到服務器主分支上,一天的工作完成,並反映給服務器。
優點:
管理方便,邏輯清晰明確,符合一般人思維習慣。
易於管理,集中式svn服務器更能保證數據安全性。
代碼一致性非常高。
適合開發人數不多的項目開發。
普及度高,大部分軟件配置管理的大學教材都是使用svn和vss。
第2章 搭建SVN服務端
2.1 安裝配置SVN服務
檢查環境
cat /etc/redhat-release
uname -r

光盤yum安裝svn
yum -y install subversion
rpm -qa subversion

建立svn版本庫數據存儲根目錄(svndata)及用戶,密碼權限目錄(svnpasswd)
mkdir -p /application/svndata --->數據存儲根目錄
mkdir -p /application/svnpasswd --->用戶,密碼權限目錄

2.2 建立項目版本庫
創建一個新的Subversion項目yunjisuan,其實,類似yunjisuan這樣的項目可以創建多個,每個項目對應不同的代碼,這里只是以創建一個項目為例演示:
svnadmin create /application/svndata/yunjisuan
tree /application/svndata/yunjisuan/ --->沒有tree則需要yum安裝
/application/svndata/yunjisuan/|-- README.txt|-- conf| |-- authz| |-- passwd| `-- svnserve.conf|-- db| |-- current| |-- format| |-- fs-type| |-- fsfs.conf| |-- min-unpacked-rev| |-- rep-cache.db| |-- revprops| | `-- 0| | `-- 0| |-- revs| | `-- 0| | `-- 0| |-- transactions| |-- txn-current| |-- txn-current-lock| |-- txn-protorevs| |-- uuid| `-- write-lock|-- format|-- hooks| |-- post-commit.tmpl| |-- post-lock.tmpl| |-- post-revprop-change.tmpl| |-- post-unlock.tmpl| |-- pre-commit.tmpl| |-- pre-lock.tmpl| |-- pre-revprop-change.tmpl| |-- pre-unlock.tmpl| `-- start-commit.tmpl`-- locks|-- db-logs.lock`-- db.lock10 directories, 28 files目錄詳解conf --->配置文件目錄authz --->用戶認證db --->數據目錄hooks --->鈎子腳本目錄locks --->代碼鎖目錄

2.3 編輯svn配置文件
cd /application/svndata/yunjisuan/conf/
ls
cp svnserve.conf{,.bak}
vim svnserve.conf

修改配置文件的如下信息
cat -n /application/svndata/yunjisuan/conf/svnserve.conf.bak | sed -n '12p;13p;20p;27p'
12 # anon-access = read13 # auth-access = write20 # password-db = passwd27 # authz-db = authz

將配置文件代碼修改為如下所示:
cat -n /application/svndata/yunjisuan/conf/svnserve.conf | sed -n '12p;13p;20p;27p'
12 anon-access = none #禁止匿名訪問13 auth-access = write #驗證訪問可寫20 password-db = /application/svnpasswd/passwd #密碼文件位置27 authz-db = /application/svnpasswd/authz #驗證文件位置

特別提示:
此配置文件里的每條配置代碼必須頂格寫,不能有空格。
2.4 將authz文件和passwd文件拷貝到/application/svnpasswd下
cp /application/svndata/yunjisuan/conf/authz /application/svnpasswd/
cp /application/svndata/yunjisuan/conf/passwd /application/svnpasswd/
ll /application/svnpasswd/

2.5 svn啟動命令幫助
svnserve --help --->svn啟動命令幫助
svnserve: warning: cannot set LC_CTYPE localesvnserve: warning: environment variable LANG is ensvnserve: warning: please check that your locale name is correctusage: svnserve [-d | -i | -t | -X] [options]Valid options:-d [--daemon] : daemon mode #守護進程啟動(后台)-i [--inetd] : inetd mode-t [--tunnel] : tunnel mode-X [--listen-once] : listen-once mode (useful for debugging)-r [--root] ARG : root of directory to serve #指定根目錄-R [--read-only] : force read only, overriding repository config file--config-file ARG : read configuration from file ARG--listen-port ARG : listen port #監聽端口默認3690[mode: daemon, listen-once]--listen-host ARG : listen hostname or IP address #監聽IP[mode: daemon, listen-once]-T [--threads] : use threads instead of fork [mode: daemon]--foreground : run in foreground (useful for debugging)[mode: daemon]--log-file ARG : svnserve log file--pid-file ARG : write server process ID to file ARG[mode: daemon, listen-once]--tunnel-user ARG : tunnel username (default is current uids name)[mode: tunnel]-h [--help] : display this help--version : show program version information

啟動svn服務
svnserve -d -r /application/svndata/
netstat -antup | grep 3690

2.6 解決svnserve啟動時的警告問題
source /etc/sysconfig/i18n --->啟用中文字符集
cat /etc/sysconfig/i18n
svnserve -d -r /application/svndata/ --->有中文字符集啟動沒有警告了

2.7 passwd文件及密碼設置
vim /application/svnpasswd/passwd
在/application/svnpasswd/passwd文件末尾追加內容
tail -4 /application/svnpasswd/passwd
yunjisuan = 123123 #設置賬號密碼benet = 123123 #設置賬號密碼stu001 = 123 #設置賬號密碼stu002 = 456 #設置賬號密碼

2.8 authz的授權
注意
1,權限配置文件中出現的用戶名必須已在用戶配置文件中定義
2,對權限配置文件的修改立即生效,不必重啟svn
權限配置說明
用戶組格式
【groups】=,其中,1個用戶組可以包含1個或多個用過戶,用戶間以逗號分隔。例如:harry\_and\_sally = harry,sally #==>用戶組 = 用戶1,用戶2
版本庫目錄格式
[<版本庫>:/項目/目錄] #例如:[repository:/baz/fuz]@<用戶組名> = <權限> #例如:@harry\_and\_sally = rw<用戶名> = <權限> #例如:harry = rw其中,方框號內部分可以有多種寫法:[/],表示根目錄及以下,根目錄是svnserve啟動時指定的,我們指定為/application/svndata,[/]就是表示對全部版本庫設置權限。[repos:/],表示對版本庫repos設置權限。[repos:/yunjisuan],表示對版本庫repos中的yunjisuan項目設置權限。[repos:/yunjisuan/benet],表示對版本庫repos中的yunjisuan項目的benet目錄設置權限。
權限主體可以是用戶組,用戶或*,用戶組在前面加@,*表示全部用戶。
權限可以是w,r,wr和空,空表示沒有任何權限。
authz中每個參數都要頂格寫,開頭不能有空格。
對於組,要以@開頭,用戶不需要@開頭。
編輯authz配置文件進行授權,在authz末尾加入以下幾句代碼
vim /application/svnpasswd/authz
egrep -v "#|^$" /application/svnpasswd/authz
[aliases][groups]sagroup = stu001,stu002 #新增本行,定義組名[yunjisuan:/] #定義授權的范圍yunjisuan = rw #用戶單獨授權benet = r #用戶單獨授權@sagroup = r #組用戶授權

authz配置文件
[game:/server]@server=rw這個含義是server用戶可以多svn的game下面的server目錄有讀寫權限[groups]#管理組manager = boss#服務端用戶組server = server1,server2#客戶端用戶組client = client1,client2#美術組art = art1,art2#策划組design=design1,design2[game:/]@manager=rw[game:/server]@server=rw[game:/client]@client=rw@design=r@art=r[game:/art]@design=rw@art=rw@client=r[game:/design]@design=rw@server=r@client=r@art=r
2.9 重啟動svnserve(可以不用重啟)
ps -ef | grep svn | grep -v grep
kill 1062
ps -ef | grep svn | grep -v grep
svnserve -d -r /application/svndata/

centos7開機自啟動svn
vim /etc/sysconfig/svnserve
--->修改成svn倉庫的路徑systemctl enable svnserve.service
--->開機啟動systemctl status svnserve
---->查看狀態

第3章 搭建SVN客戶端
3.1 使用svn客戶端(windows版)
3.1.1 軟件版本選擇
推薦:TortoiseSVN-1.9.7.27907-x64-svn-1.9.7
注意:32位系統要用32位軟件版本下載鏈接
鏈接:https://pan.baidu.com/s/1dKq_JVJN3tFxY_AvMKKTcA
提取碼:kn9z
3.1.2 svn客戶端軟件安裝
一路yes即可
3.1.3 svn客戶端軟件的使用
(1)先在本地創建一個目錄,起名任意,比如data

(2)鼠標右鍵點擊data目錄
svn://192.168.200.69/yunjisuan
選擇右鍵菜單里的SVN Checkout,出現下圖:

特別提示
如果連接不通,請檢查Linux虛擬機的iptables是否關閉
點擊OK后,出現下圖:

再次點擊OK以后,結束。此時目錄里多了一個隱藏的目錄,表示此目錄已經和svn服務器連通

命令說明
(1)SVN Checkout:相當於下載,第一次連接svn服務器的時候需要和服務器的對應存儲目錄進行數據同步,如果服務器的對應目錄里有數據文件,那么就會下載到你的本地對應目錄里。
(2)SVN Update:更新數據,檢查服務器端svn存儲目錄里是否和本地svn存儲目錄數據不一致,如果不一致,那么下載改變或新增的部分到本地svn目錄里。(不會刪除本地目錄內容)
(3)SVN Commit:提交數據到svn服務器端存儲目錄。本地svn存儲目錄會和服務器端存儲目錄進行比對校驗。會把本地改變的部分和新增的部分同步上傳至服務器端。
3.1.4 svn客戶端使用測試
(1)向windows的svn存儲目錄data里放一個空文件

(2)右鍵點擊data目錄,選擇SVN Commit


(3)打開本地data目錄里的文件,隨便寫點內容后,再次進行SVN commit


(4)直接從本地查看服務器端的數據內容
右鍵點擊本地svn存儲目錄data,選擇TortoiseSVN ===>Repo-browser后出現下圖

雙擊文件可以直接遠程打開文件,可以看到里面剛剛被修改后的內容已經更新至服務器端。
(5)刪除本地svn存儲目錄data里的文件,后選擇SVN Update
會發現,剛剛刪除的文件又重新下載回來了。
(6)繼續刪除本地svn存儲目錄data里的文件,后選擇SVN Commit

(7)再次查看服務器端存儲目錄里,發現文件已經被刪除了

3.2 SVN的管理命令(Linux)
svn --help
usage: svn <subcommand> [options] [args]Subversion command-line client, version 1.6.11.Type 'svn help <subcommand>' for help on a specific subcommand.Type 'svn --version' to see the program version and RA modulesor 'svn --version --quiet' to see just the version number.Most subcommands take file and/or directory arguments, recursingon the directories. If no arguments are supplied to such acommand, it recurses on the current directory (inclusive) by default.Available subcommands:addblame (praise, annotate, ann)catchangelist (cl)checkout (co) #下載數據cleanupcommit (ci) #提交數據copy (cp)delete (del, remove, rm)diff (di)exporthelp (?, h)importinfolist (ls) #顯示服務器端內容locklogmergemergeinfomkdirmove (mv, rename, ren)propdel (pdel, pd)propedit (pedit, pe)propget (pget, pg)proplist (plist, pl)propset (pset, ps)resolveresolvedrevertstatus (stat, st)switch (sw)unlockupdate (up) #更新數據Subversion is a tool for version control.For additional information, see http://subversion.tigris.org/

3.2.1 從SVN庫提取數據
將文件checkout到本地目錄
svn checkout(co) remotepath localpathmkdir yunjisuan
cd yunjisuan/
pwd

下載服務器端數據到Linux本地目錄
svn co svn://192.168.200.69/yunjisuan/ /root/yunjisuan/ --username=benet --password=123123
ll

3.2.2 查看SVN版本庫中的數據
svn list file:///application/svndata/yunjisuan

3.2.3 提交數據到SVN版本庫
(1)一次失敗的提交
pwd
mkdir [1..5]
ll
svn add * --->提交前需要先把要提交的內容做標記A(相當於windows上勾對號)
svn ci -m "message" --->提交時需要同時-m指定一段話作為備注
A 1A 2A 3A 4A 5svn: warning: '666.txt.txt' is already under version control --->這個文件已經標記過了
svn: Commit failed (details follow):svn: Authorization failed #提交失敗,賬戶沒有寫權限,認證失敗

(2)換賬戶重新Checkout
svn co svn://192.168.200.69/yunjisuan/ /root/yunjisuan/ --username=yunjisuan --password=123123
換擁有寫入權限的賬戶checkoutStore password unencrypted (yes/no)? yes --->是否作為目錄的新賬戶和密碼
ll

重新提交
svn add *
svn: warning: '1' is already under version controlsvn: warning: '2' is already under version controlsvn: warning: '3' is already under version controlsvn: warning: '4' is already under version controlsvn: warning: '5' is already under version controlsvn: warning: '666.txt.txt' is already under version control --->這些文件已經標記過了
svn ci -m "message" --->重新提交

查看服務器端數據
svn list file:///application/svndata/yunjisuan/

第4章 SVN鈎子腳本
4.1 鈎子腳本簡介
鈎子腳本的具體寫法就是操作系統中shell腳本程序的寫法,可根據自己的SVN所在的操作系統和shell程序進行相應的開發。
鈎子腳本就是被某些版本庫事件觸發的程序,例如:創建新版本或修改未被版本控制的屬性。每個鈎子都能掌管足夠的信息來了解發生了什么事件,操作對象是什么以及觸發事件用戶的賬號。
根據鈎子的輸出或返回狀態,鈎子程序能夠以某種方式控制該動作繼續執行,停止或掛起。
默認情況下,鈎子的子目錄中包含各種版本庫鈎子模板
ls -l /application/svndata/yunjisuan/hooks/
對每種Subversion版本庫支持的鈎子都有一個模板,通過查看這些腳本的內容,你能看到是什么事件觸發了腳本及如何給傳腳本傳遞數據。
同時,這些模板也是如何使用這些腳本,結合Subversion支持的工具來完成有用任務的例子。
要實際安裝一個可用的鈎子,你需要在repos/hooks目錄下安裝一些與鈎子同名(如start-commit或者post-commit)的可執行程序或腳本,注意,去掉模板的擴展名。

重要提示
由於安全原因,Subversion版本庫在一個空環境中執行鈎子腳本就是沒有任何環境變量,甚至沒有$PATH或%PATH%。由於這個原因,許多管理員會感到很困惑,他們的鈎子腳本手工運行時正常,可在Subversion中卻不能運行。要注意,必須在你的鈎子中設置好環境變量或為你的程序指定好絕對路徑。
4.2 SVN的hooks模板
4.2.1 常用鈎子腳本

4.2.2 非常用鈎子腳本
pre-revprop-change:在修改revision屬性之前,執行該腳本
post-revprop-change:在修改revision屬性之后,執行該腳本。因為修改稿已經完成,不可更改,因此本腳本的返回值被忽略(不過實際上的實現似乎是該腳本的正確執行與否影響屬性修改)
pre-unlock:對文件進行解鎖操作之前執行該腳本
post-unlock:對文件進行解鎖操作之后執行該腳本
pre-lock:對文件進行加鎖操作之前執行該腳本
post-lock:對文件進行加鎖操作之后執行該腳本。
4.2.3 利用鈎子腳本觸發同步數據的注意事項
(1)一定要定義變量,主要是用過的命令的路徑。因為SVN的考慮的安全問題,沒有調用系統變量,如果手動執行是沒有問題,但SVN自動執行就會無法執行了。
(2)SVN的同步目錄在 update之前一定要先checkout一份出來,還有這里一定要添加用戶和密碼。
(3)加上了對前一個命令的判斷,如果update的時候出了問題,程序沒有退出的話還會繼續同步代碼到Web服務器上,這樣會造成代碼有問題。
(4)建議最好記錄日志,出錯的時候可以很快的排錯
(5)最后是數據同步,rsync的相關參數一定要清楚。
4.3 svn鈎子生產應用場景舉例
pre-commit:
限制上傳文件擴展名及大小,控制提交要輸入的信息等。post-commit:
SVN更新自動通知,MSN,郵件或短信通知。
SVN更新觸發checkout程序,然后實時rsync推送到服務器等。
4.4 svn鈎子生產應用實戰
4.4.1 rsync與svn鈎子結合實現數據實時同步某企業小案例
(1)建立同步WEB目錄
mkdir -p /data/www
(2)將SVN中內容checkout到WEB目錄一份。
[root@localhost yunjisuan]# mkdir -p /data/www[root@localhost yunjisuan]# svn checkout svn://192.168.0.220/yunjisuan /data/www --username=yunjisuan --password=123123A /data/www/xxxxA /data/www/111A /data/www/120A /data/www/112A /data/www/113A /data/www/114A /data/www/ffff.txtA /data/www/115A /data/www/116A /data/www/117A /data/www/118A /data/www/119Checked out revision 7.[root@localhost yunjisuan]# ll /data/www/total 44drwxr-xr-x. 3 root root 4096 Sep 13 21:32 111drwxr-xr-x. 3 root root 4096 Sep 13 21:32 112drwxr-xr-x. 3 root root 4096 Sep 13 21:32 113drwxr-xr-x. 3 root root 4096 Sep 13 21:32 114drwxr-xr-x. 3 root root 4096 Sep 13 21:32 115drwxr-xr-x. 3 root root 4096 Sep 13 21:32 116drwxr-xr-x. 3 root root 4096 Sep 13 21:32 117drwxr-xr-x. 3 root root 4096 Sep 13 21:32 118drwxr-xr-x. 3 root root 4096 Sep 13 21:32 119drwxr-xr-x. 3 root root 4096 Sep 13 21:32 120-rw-r--r--. 1 root root 30 Sep 13 21:32 ffff.txt-rw-r--r--. 1 root root 0 Sep 13 21:32 xxxx
(3)制作鈎子腳本,post-commit
root@localhost yunjisuan]# cd /application/svndata/yunjisuan/hooks/[root@localhost hooks]# cp post-commit.tmpl post-commit #復制模板一份[root@localhost hooks]# egrep -v "#|^$" post-commit #模板原始內容REPOS="$1"REV="$2"mailer.py commit "$REPOS" "$REV" /path/to/mailer.conf[root@localhost hooks]# vim post-commit #修改post-commit腳本[root@localhost hooks]# egrep -v "#|^$" post-commitREPOS="$1" #傳參(未用上)REV="$2" #傳參(未用上)SvnIP="192.168.200.69" #svn服務端的IP地址ProjectName="yunjisuan" #svn服務端的項目庫名稱UserName="yunjisuan" #賬戶姓名PassWord="123123" #賬戶密碼LocalPath="/data/www" #位於svn本地的共享目錄SVN=/usr/bin/svn #svn命令的絕對路徑export LC_CTYPE="en_US.UTF-8" #中文字符集支持export LC_ALL=if [ ! -d ${LocalPath} ];thenmkdir -p ${LocalPaht}$SVN checkout svn://${SvnIP}/${ProjectName} ${LocalPath} --username=${UserName} --password=${PassWord} #新創建目錄需要先經過checkout才能updateelse$SVN update --username yunjisuan --password 123123 /data/www #更新共享目錄內容fiif [ $? -eq 0 ];then/usr/bin/rsync -az --delete /data/www /tmp/ #數據同步推送到本地/tmp目錄下(生產環境可以直接同步推送到Web測試服務器)fi
(4)進行鈎子腳本同步測試
#刪除之前的測試記錄[root@localhost hooks]# rm -rf /data/www/[root@localhost hooks]# ll -d /data/wwwls: cannot access /data/www: No such file or directory[root@localhost hooks]# rm -rf /tmp/*[root@localhost hooks]# ll /tmp/total 0[root@localhost hooks]# chmod 700 post-commit #給鈎子腳本可執行權限
特別提示
當用戶通過svn更新鈎子post-commit所在的項目庫時,在更新完畢之后會自動觸發鈎子腳本
模擬更新項目庫版本


查看svn服務器端鈎子腳本執行情況
[root@localhost hooks]# ll /data/www/ #svn服務器端本地共享目錄total 28drwxr-xr-x. 3 root root 4096 Sep 13 23:07 111drwxr-xr-x. 3 root root 4096 Sep 13 23:07 112drwxr-xr-x. 3 root root 4096 Sep 13 23:07 113drwxr-xr-x. 3 root root 4096 Sep 13 23:07 116drwxr-xr-x. 3 root root 4096 Sep 13 23:07 117drwxr-xr-x. 3 root root 4096 Sep 13 23:07 118-rw-r--r--. 1 root root 0 Sep 13 23:07 test.txt-rw-r--r--. 1 root root 9 Sep 13 23:07 xxx.txt-rw-r--r--. 1 root root 0 Sep 13 23:07 xxxx[root@localhost hooks]# ll /tmp/www/ #推送后的數據目錄total 28drwxr-xr-x. 3 root root 4096 Sep 13 23:07 111drwxr-xr-x. 3 root root 4096 Sep 13 23:07 112drwxr-xr-x. 3 root root 4096 Sep 13 23:07 113drwxr-xr-x. 3 root root 4096 Sep 13 23:07 116drwxr-xr-x. 3 root root 4096 Sep 13 23:07 117drwxr-xr-x. 3 root root 4096 Sep 13 23:07 118-rw-r--r--. 1 root root 0 Sep 13 23:07 test.txt-rw-r--r--. 1 root root 9 Sep 13 23:07 xxx.txt-rw-r--r--. 1 root root 0 Sep 13 23:07 xxxx> 綜上,post-commit鈎子腳本測試成功。
4.4.2 通過pre-commit的鈎子腳本還可以對用戶上傳的內容進行大小和擴展名的限制
因為並不常用,這部分內容,我們略過
第5章 大中小型企業上線解決方案
5.1 SVN 上線解決方案說明
5.1.1 小型公司代碼上線案例(十幾台服務器)

開發每次修改完代碼就直接提交,然后通過FTP直接更新到Web服務器網頁目錄;沒有專門的測試人員,完全是由用戶來進行測試體驗。
小型企業現狀
小型公司一般只有幾個開發人員,網站核心程序大多數都是PHP語言開發,為了方便,會直接通過FTP直接上傳程序代碼到線上服務器,隨時隨地上線更新。
上述上線方案的特點和問題
發布快,及時,隨時隨地就可以發布代碼。
開發人員發布的代碼不經過測試人員的測試,且用戶訪問頁面刷新后頁面即改變,也可能刷新瞬間程序在更新,到時無法訪問,對網站用戶的體驗比較差,如果開發寫錯了代碼,造成的影響就更大了,這是拿用戶作為測試的上線方案。
據統計,網站中大概50%以上的故障是和開發程序代碼有關的,(比如:開發寫錯了一個循環代碼,導致了死循環,此時大量用戶訪問這個程序,就能把服務器資源耗盡,搞死服務器)
在中小公司網站出了問題一般是運維人員的問題(例如網站宕機),但這種情況下,問題大多可能由開發人員或代碼引起的,這里比較好的策略是開發項目負責制思想。
小型企業上線架構方案建議
開發人員需在個人電腦搭建LAMP環境測試開發好的網站代碼,並且在辦公室或IDC機房的測試環境測試通過,最好有專職測試人員。
程序代碼上線規定時間,例如,三天上線一次,如網站需經常更新可每天下午17點上線,這個看網站業務性質而定,原則就是影響用戶體驗最小。
代碼上線之前需備份,網站程序出了問題方便回退,另外,網站程序出了問題方便回退,另外,從上線技巧上講,上傳代碼時盡可能先傳到服務器網站臨時目錄,傳完整后一步mv過去,或者通過ln做軟連接。(線上更新代碼思路)
務必由運維人員管理上線,對於代碼的功能性,開發人員更在意,而對於代碼的性能和服務的穩定,運維更在意,因此,如果網站問題歸運維管,就要讓運維上線這樣更規范科學。否則,開發隨意更新,出了問題運維負責,這樣就錯了。
5.1.2 中型企業上線解決方案
中型企業上線,一般是規范運維人員操作步驟,制定統一的上線操作腳本,備份文件名稱,備份文件路徑。使操作人性化,統一化,自動化。
Web代碼的上線流程演示圖

5.1.3 大型企業上線解決方案
大型企業上線一般制度和流程控制較多,比較嚴謹,下面是某大型企業上線解決方案架構:

SVN里的內容:
1,程序代碼
2,服務的配置
3,項目文檔,設計文檔,運維部署優化文檔
門戶大型網站架構環境代碼上線具體方案
本地開發人員從SVN中取代碼。當天上線的提交到trunk,否則,長期項目單開分支開發,然后在合並主線(trunk)
辦公內網開發測試時,由開發人員或配置管理員通過部署平台jenkins實現統一部署,(即在部署平台上控制開發機器從SVN取代碼,編譯,打包,發布到開發機器,包名如idc_dep.war)
開發人員通知或和測試人員一起測試程序,沒有問題后,打上新的tag標記。
配置管理員,根據上步的tag標記,checkout出上線代碼,並配置好IDC測試環境的所有配置,執行編譯,打包(mvn,ant)(php不需要),然后發布到IDC內的統一分發服務器,這里要注意,不同環境的配置文件是隨代碼同時發布的。
配置管理員或SA上線人員,把分發的程序代碼內容推送到相關測試服務器(包名如idc_test.war),然后通知開發及測試人員進行測試。如果有問題向上回退,繼續修改。
如果測試沒有問題,繼續打好tag標記,此時,配置管理員,根據上步的tag標記,checkout出測試好的代碼,並配置好IDC正式環境的所有配置,執行編譯,打包(mvn,ant)(php不需要),然后發布到IDC內的統一分發服務器主機,准備批量發布。
配置管理員或SA上線人員,把分發的內容推送到相關正式服務器(包名如idc_product.war),然后通知開發及測試人員進行測試。如果有問題直接發布回滾指令。
IDC正式上線的過程對於JAVA程序,可以是AB分組上線的思路,即平滑下線一半的服務器,然后發布更新代碼測試,無問題后,掛上服務器,同時在平滑下線另一半的服務器,然后發布更新代碼測試(或者直接發布后就掛上線)
PHP程序代碼上線的具體方案
對於PHP上線方法:發布代碼時(也需要測試流程)可以直接發布到正式線臨時目錄,然后mv或更改link的方式發布到正式線目錄,不需要重啟http服務。這是sina,ganji的上線方案。
JAVA程序代碼上線的具體方案
對於java上線方法:較大公司需要分組平滑上線,例如,首先從負載均衡器上摘掉一半的服務器,發布代碼后,重啟服務器測試,沒問題后,掛上經過測試的這一半,再下另外一半。如果前端有DNS智能解析,上線還可以分地區上線若干服務器,逐漸普及到全國的服務器,這個被稱為灰度發布。
5.1.4 更多大型代碼上線解決方案案例
SINA網的代碼發布流程邏輯圖

(2)和訊案例
ABCD 12:33:24我們這里代碼發布都不太標准,全部都是開發自己搞Mr.chen 12:35:14目前是什么個方式呢說下現狀即可。ABCD 12:36:04就是很傳統,開發有權限可以上機器,我們就把應用部署好,他們隨便折騰。ABCD 12:41:05源代碼是svn,靜態內容都是同步分發
(3)小米案例
XYZ 13:36:49代碼上線都是開發上,我們運維這邊沒有流程...如果代碼發布導致了問題,就是開發的問題。XYZ 13:37:55服務器上面有一個客戶端,開發自己在頁面上點發布,客戶端就去拉代碼了。就是這么個額流程,就像你以前說的,項目責任制,誰的項目出問題了。找開發和運維Mr.chen 13:49:08不需要重啟服務器么?還有直接拉到站點目錄么?XYZ 13:49:17嗯,都是自動的他們有個管理系統Mr.chen 13:49:49如何保證不影響用戶呢?還有怎么回滾的。XYZ 13:50:12還沒有做到這點把那個管理系統可以回滾的,好像平時把客戶的部署上去,再把機器加入到那個系統中他們就可以發了。XYZ 13:58:16運維這邊就管添加機器和安裝客戶端,也有發布權限,項目上線后很少發。一教就會沒有在這塊搞過太多,那個程序和版本管理結合的。實現原理應該就是客戶端收到服務器發來的clone命令和路徑,就去執行了。
什么是配置管理員呢
就是在開發和運維中間起一個連接紐帶的一個職位,這個職位一般在大公司里會設置,負責SVN的管理,上線管理,申請,協調等工作。
5.2 自動化部署和上線代碼管理
對於門戶網站或重視規范或開發能力較強的公司也許會結合系統服務和WEB界面管理來更科學更自動的進行上線代碼管理,如開發一個自動化代碼上線部署平台,其實就是一個web管理界面(界面底層調用相關腳本實現分發推送代碼以及重啟服務器),然后普通的初級上線人員就可以在平台里實現僅僅點鼠標,敲回車,就能實現平滑上線和平滑回滾代碼了,當然,自動化和完善的程度也許沒我們說的這么好,但是,思路是這樣的。下面就是管理平台的一個圖例:

開發自動化部署平台的思路很多,例如:我們可以通過nagios的被動模式實現上線管理平台原理思路
實際上就是生成配置在分發服務器上執行命令請求,應用服務器,然后腳本在應用服務器處理完畢后回傳結果到web界面顯示:
例如:check_nrpe -h 10.0.0.178 -c check_load
5.3 開發人員和運維人員業務變更管理平台
業務變更管理平台優點
(1)變更管理制度流程有利於業務穩定。
(2)保留變更業務歷史,便於核查發現的問題。
(3)故障跟蹤平台,有利於跟蹤問題的解決進度,而不是半途而廢。
(4)相關常用軟件(有時間最好研究一下)
JIRA 用於缺陷跟蹤,客戶服務,需求收集,流程審批,任務跟蹤,項目跟蹤和敏捷管理等工作領域。
Mantis是一款PHP開源Bug跟蹤系統,比較適合中小型項目的管理及跟蹤,具有多特性。包括:易於安裝,易於操作,基於Web,支持任何可運行PHP的平台(Windows,Linux,Mac,Solaris,AS400/i5等),已經被翻譯成68種語言,支持多個項目,為每一個項目設置不同的用戶訪問級別,跟蹤缺陷變更歷史,定制我的視圖頁面,提供全文搜索功能,內置報表生成功能(包括圖形報表),通過Email報告缺陷,用戶可以監視特殊的Bug,附件可以保存在web服務器上或數據庫中(還可以備份到FTP服務器上),自定義缺陷處理工作流,支持輸出格式包括csv,MicrosoftExcel,MicrosoftWord,集成源代碼控制(SVN與CVS),集成wiki知識庫與聊天工具(可選/可不選),支持多種數據庫(MySQL,MSSQL,PostgreSQ,Oracle,DB2),提供WebService(SOAP)接口,提供Wap訪問。
