svnsync同步備份svn版本庫 前言大家都知道,代碼對整個IT公司來說就是生命,小中型公司由於人員水平問題,大部分都採用svn進行代碼的版本化控制,因此svn的版本庫備份顯得至關重要,這裡我介紹svnsync實現svn的版本庫同步,並且將實現過程指令碼化 www.2cto.com 需求同步的主要版本庫位於A伺服器(192.168.1.1),基於apache進行存取控制,配置根目錄下有test[1-9]這9個版本庫,採用http協議進行訪問鏡像版本庫位於B伺服器(192.168.1.2),基於apache進行存取控制,採用http協議進行訪問 授權存取控制由於主要版本庫和鏡像版本庫都採用libapache2-svn模組進行許可權存取控制,因此我們首先需要提供一個svn檢出使用者,該使用者對於A、B伺服器上的所有版本庫均具有讀寫權限假設該svn檢出使用者為:[html] --username root --password root 鏡像伺服器建立目標版本庫 www.2cto.com 建立版本庫鏡像伺服器B需要建立同主伺服器A名稱相同的版本庫,這樣才能進行同步備份採用svnadmin create命令進行建立版本庫 修改目標庫的pre-revprop-change原始碼[html] #!/bin/bash REPOS="$1" REV="$2" USER="$3" PROPNAME="$4" ACTION="$5" if [ "$ACTION" = "M" -a "$PROPNAME" = "svn:log" ]; then exit 0; fi echo "Changing revision properties other than svn:log is prohibited" >&2 exit 1 指令碼閱讀如果修改的是svn:log屬性,則返回0,允許修改,其它的屬性則返回-1,不允許修改我們需要修改版本庫的所有屬性,因此我們需要此指令碼直接返回0成功,因此需要將exit -1改為exit 0 修改後代碼[html] #!/bin/bash REPOS="$1" REV="$2" USER="$3" PROPNAME="$4" ACTION="$5" if [ "$ACTION" = "M" -a "$PROPNAME" = "svn:log" ]; then exit 0; fi echo "Changing revision properties other than svn:log is prohibited" >&2 exit 0 實現指令碼(bash)[html] #!/bin/bash #變數定義 svnstorage=("test1" "test2" "test3" "test4" "test5" "test6" "test7" "test8" "test9") svndir="/srv/svn" if [ ! -d $svndir ]; then mkdir -p $svndir chown -R www-data.www-data $svndir fi #迴圈建立目標版本庫 for svn in ${svnstorage[*]} do #刪除已有的svn版本庫 if [ -d $svndir/$svn ]; then rm -r $svndir/$svn fi #建立目標版本庫 svnadmin create $svndir/$svn #修改pre-revprop-change cp $svndir/$svn/hooks/pre-revprop-change.tmpl $svndir/$svn/hooks/pre-revprop-change chmod +x $svndir/$svn/hooks/pre-revprop-change sed -i "s/exit 1/exit 0/g" $svndir/$svn/hooks/pre-revprop-change #修改版本庫屬主(svn通過apache使用http協議訪問,因此屬主為www-data) chown -R www-data.www-data $svndir/$svn done 初始化&&同步 初始化命令初始化,建立目標庫與源庫之間的同步關係 [html] svnsync initialize 目標庫URL 源庫URL 同步命令[html] svnsync synchronize 目標庫URL 實現指令碼為了實現鏡像版本庫的同步,因此將可以同時訪問A&&B伺服器上的版本庫的使用者名稱和密碼用變數的方式寫在了指令碼中 [html] #!/bin/bash #變數定義 svnstorage=("test1" "test2" "test3") svndir="/srv/svn" if [ ! -d $svndir ]; then mkdir -p $svndir chown -R www-data.www-data $svndir fi #迴圈建立目標版本庫 for svn in ${svnstorage[*]} do #刪除已有的svn版本庫 if [ -d $svndir/$svn ]; then rm -r $svndir/$svn fi #建立目標版本庫 svnadmin create $svndir/$svn #修改pre-revprop-change cp $svndir/$svn/hooks/pre-revprop-change.tmpl $svndir/$svn/hooks/pre-revprop-change chmod +x $svndir/$svn/hooks/pre-revprop-change sed -i "s/exit 1/exit 0/g" $svndir/$svn/hooks/pre-revprop-change #修改版本庫屬性 chown -R www-data.www-data $svndir/$svn done #初始化&&同步目標版本庫 localip="192.168.1.2" remoteip="192.168.1.1" username="root" password="root" for svn in ${svnstorage[*]} do #初始化 svnsync initialize http://$localip/svn/$svn http://$remoteip/svn/$svn --username $username --password $password #同步 if [ $? -eq 0 ]; then svnsync synchronize http://$localip/svn/$svn --username $username --password $password fi done 鏡像伺服器同步更新 需求以A伺服器的test1版本庫為例,如果有人提交代碼到test1,相應的B伺服器的鏡像版本庫test1需要同步更新 post-commit鉤子自動同步在A伺服器源庫test1的hooks目錄下的post-commit指令碼裡增加如下代碼: [html] SVNSYNC=/usr/bin/svnsync $SVNSYNC sync --non-interactive http://目標庫URI --username root --password root www.2cto.com 鏡像版本庫與源庫UUID一致性問題通過svnlook來查看鏡像版本庫和源庫的uuid是否一致,如果不一致,可以採用如下方法:查看源庫的uuid [html] svnlook uuid $svn_path 更新鏡像庫的uuid [html] sudo svnadmin setuuid $svn_path $源庫uuid 查看更新後的鏡像庫的uuid [html] svnlook uuid $svn_path 更新svn提交地址到鏡像版本庫 命令[html] svn switch --relocate http://oldcheckpath http://newcheckpath 來源 http://blog.csdn.net/zinss26914/article/details/8601458