2010年9月1日 星期三

[應用程式] git via http

在git協同工作模式下,會根據不同角色設定RW和RO的權限,一般來說透過ssh的存取通常為RW,透過curl/http(s)通常為RO(若不使用WebDAV),前面介紹過以Gitosis管理ssh存取的安裝設定方式,本篇紀錄透過http存取的安裝設定方式

1. http via gitweb,如git.kernel.org

下載安裝gitweb
$ sudo apt-get install gitweb

修改gitweb設定檔,主要是設定repository的目錄(本篇沒有修改)
$ sudo vim /etc/gitweb.conf
$projectroot = "/var/cache/git"

複製gitweb目錄
$ sudo cp /usr/share/gitweb /var/www/
$ sudo cp /usr/lib/cgi-bin /var/www/gitweb

用htpasswd設定foobar密碼(第一次建立加上 -c)
$ sudo /usr/local/apache2/bin/htpasswd -c /usr/local/apache2/conf/git-auth-file foobar

修改httpd.conf內容
$ sudo vim /usr/local/apache2/conf/httpd.conf
Alias /gitweb /var/www/gitweb
<Directory /var/www/gitweb>
  SetEnv GITWEB_CONFIG /etc/gitweb.conf
  Options ExecCGI
  AddHandler cgi-script cgi
  DirectoryIndex /gitweb/cgi-bin/gitweb.cgi
  AuthType Basic
  AuthName "gitweb"
  AuthUserFile /usr/local/apache2/conf/git-auth-file
  Require valid-user
  Order allow,deny
  Allow from all
  AllowOverride None
</Directory>

在git-server上建立kernel_source,詳細過程參考Gitosis HOWTO
$ sudo vim /path/to/gitosis-admin/gitosis.conf
[repo kernel_source]
owner = foo@git-client-foo
gitweb = yes
description = kernel source development

從git-server上將repository取回
$ git clone git@git-server:kernel_source
$ cd kernel_source
$ touch README
$ git add README
$ git commit -am '[add] README'
$ git push origin master

建立kernel_source.git在/var/cache/git目錄下
$ sudo git clone --bare kernel_source /var/cache/git/kernel_source.git

修改讀取權限
$ cd /var/cache/git/kernel_source.git
$ sudo git update-server-info

用瀏覽器看結果
http://git-server/gitweb

修改gitweb的頁面中description和owner欄位
$ sudo vim /var/cache/git/kernel_source.git/description
this is kernel source

$ sudo vim /var/cache/git/kernel_source.git/config
[gitweb]
owner = "foobar"



2. http via curl

如果沒有建立git-server,一樣可以建立用http存取的git服務
$ mkdir kernel_source
$ cd kernel_source
$ git init
$ touch README
$ git add README
$ git commit -am '[add] README'

建立kernel_source.git在/var/www/html目錄下(步驟與上面相同, 只有目錄不同)
$ sudo git clone --bare kernel_source /var/www/html/kernel_source.git

修改讀取權限(步驟與上面相同, 只有目錄不同)
$ cd /var/www/html/kernel_source.git
$ sudo git update-server-info

用htpasswd設定foobar密碼(第一次建立加上 -c)
$ sudo /usr/local/apache2/bin/htpasswd -c /usr/local/apache2/conf/git-auth-file foobar

為了要能讓用http抓下的code可以push回去,必須開啟webdav,而首先要先確定apache是否有載入dav和dav_fs模組,可以透過apachectl查看目前已載入的模組
$ /path/to/apache2/bin/apachectl -t -D DUMP_MODULES
dav_module (shared)
 dav_fs_module (shared)
 dav_lock_module (shared)
 dav_svn_module (shared)

如果沒有載入,一種就是用a2enmod指令手動載入需要的模組
$ a2enmod dav
$ a2enmod dav_fs
或是重新config和install,例如
$ configure --enable-dav --enable-dav-fs

當dav的模組都載入後,修改httpd.conf內容
DavLockDB /var/lock/dav/lockdb
<Directory "/var/www/html/kernel_source.git">
  Dav on
  Options FollowSymLinks Indexes ExecCGI
  AuthType Basic
  AuthName "gitweb"
  AuthUserFile /usr/local/apache2/conf/git-auth-file
  Require valid-user
  Order allow,deny
  Allow from all
  AllowOverride None
</Directory>

由於加上apache的basic authentication, 因此在使用curl時需先加上帳號密碼的驗證
$ vim ~/.netrc
# add
machine git-server
login foobar
password ooxx

測試看看是否可正常連線
$ curl --netrc --location -v http://git-server/kernel_source.git

如果看到類似這樣的內容就是正確的結果了
<html>
<head>
<title>Index of /kernel_source.git</title>
</head>
<body>
<h1>Index of /kernel_source.git</h1>
<ul><li><a href="/"> Parent Directory</a></li>
<li><a href="HEAD"> HEAD</a></li>
<li><a href="branches/"> branches/</a></li>
<li><a href="config"> config</a></li>
<li><a href="description"> description</a></li>
<li><a href="hooks/"> hooks/</a></li>
<li><a href="info/"> info/</a></li>
<li><a href="objects/"> objects/</a></li>
<li><a href="packed-refs"> packed-refs</a></li>
<li><a href="refs/"> refs/</a></li>
</ul>
</body></html>

使用curl讀取kernel_source.git
$ git clone http://git-server/kernel_source.git


由於我還不知道本地repository更新後, 要如何更新repository.git的內容, 所以我每次都要砍掉重練, 而有鑑於砍掉重練的步驟頗重複, 所以我寫了一個update_repo_git.sh處理
#!/bin/bash
git_repo_path="/home/foobar/git"
git_http_path="/var/www/html"
git_web_path="/var/cache/gitweb"

while [ $# -gt 0 ]
do
  # git http access
  rm -Rf "$git_http_path"/"${1}".git
  git clone --bare "$git_repo_path"/"${1}" "$git_http_path"/"${1}".git
  cd "$git_http_path"/"${1}".git
  git update-server-info

  # change folder permission for webdav
  chown -R daemon:daemon "$git_http_path"/"${1}".git

  # gitweb access
  rm -Rf "$git_web_path"/"${1}".git
  git clone --bare "$git_repo_path"/"${1}" "$git_web_path"/"${1}".git
  cd "$git_web_path"/"${1}".git
  git update-server-info
  shift
done

未來若是repository時, 要同步更新gitweb和web上的repository(可同時加上多個repo名稱)
$ ./update_repo_git.sh kernel_source
就可透過gitweb查看,只要在瀏覽器的網址列輸入http://git.server/gitweb即可
並可透過http的方式下載,只要下git clone http://git.server/kernel_source.git即可


參考資料:
* Learn GIT series – Part 2: Install GITWEB to host repository on Apache web-server
* Debian Linux 架設 Gitweb
* Debian Linux 架設使用 HTTP 存取 的 Git Server

沒有留言: