Git服务器、http协议及XCode
本来费了老鼻子牛劲搭好了SVN,可以通过web进行访问,也弄好了eclipse和XCode,结果几个开发的同事说要上git,悲了个催,又开始折腾git。
因为公司只有一个公网的http出口,因此开始了web上的git之路。目标是通过web在公司内部的git服务器上进行代码管理,必须实现简单的权限设置(指定的人才能读写)。因为一开始就奔web去,结果半桶水荡啊荡的,发现怎么都搞不定。因此悟出了个道理,研究一个东西,不管目标是什么,一定得从头开始,而且必须一个一个动手试,这样才能理解基础知识,否则过程中很多东西会因为一知半解而失败。到现在,终于完成了git服务器、ssh协议、http协议进行clone、push和pull,以及xcode集成的git可以push。
思路:需要安装的组件:git、gitosis(实现git的基本权限)、git-core、gitweb。涉及的机器有客户机(开发用)和服务器。无论是客户端还是服务器都必须安装git(xcode内置了git)。服务器要作为git仓库无需工作区、暂存区,通过--bare参数建立裸仓库。git服务可以通过多种协议向客户端提供服务(本地传输,SSH 协议,Git 协议和 HTTP 协议,可以参看《服务器上的 Git - 协议》),开始一上来就试web,结果走了很多弯路,安装gitweb可以参见《在Ubuntu 14.04上配置 gitweb》,但折腾了半天总是出现不知道命令中的地址怎么填,或权限怎么配的问题,因此静下心来从基础做起,先做ssh,再实现http。
首先是安装配置git和gitosis,实现在命令行和XCode中通过ssh协议从服务端clone、pull以及push。此间参考下面的资料1~4。
然后是安装gitweb和git-core,实现在命令行通过http协议clone项目,XCode中通过http协议从服务器push。
关于参考资料:
1、《搭建ubuntu上的git服务器,并用Mac下用Xcode连接进行开发》:这个详细讲述了gitosis的安装及简单配置,按照它实施至少可以实现用客户端管理服务器的gitosis及裸仓库,并可以实现手工进行clone、pull、push。其中涉及到ssh生成rsa密码文件以及在ssh协议中的使用。将在服务器的git/.ssh目录下生成authorized_keys文件,一行一个用户,这些用户都是ssh客户端,可以用来免密码。
2、《服务器 Gitosis 架设指南》:这里涉及了gitosis的配置,比上文要详细。注意git remote add origin git@192.168.1.115:foo.git命令,在后面XCode中要用到。
3、《gitosis安装配置详细过程》:这个对gitosis的配置解释也比较好。
需要记录的是在gitosis中走过的弯路有:客户端生成的rsa文件自动用user@machinename.local为名字建立rsa文件(这个名字在id_rsa.pub文件中末尾),在初始化gitosis的时候并不能更改这个名字,即使按照上文中写的改rsa.pub文件名来初始化也一样的会以带@符号的名字出现在gitosis中。当时为了改掉这个@符号,我复制了一个pub文件,改名后在客户端添加到keydir中,再commit和push到服务器,结果吧gitosis弄坏了,原因是两个内容相同但名字不同的文件导致gitosis没法鉴权。用户名后来是直接改上述的authorized_keys文件中的靠前的那个名字来实现。
4、《理解 XCode 中的 Git 版本控制》:这个详细讲述了XCode中的Git,两种本地git库的建立方式,一个是新建项目时自动建,一个是已有项目用命令行方式建。这还只是本地git仓库的实现。
需要记录的是XCode中远程仓库的添加,6.1版本的repository在preferences中,整了几次都失败了,估计是使用了错误的用户名或连接方式,最终成功的方法是用命令行:git remote add test@server git@serverip:test.git,其中test@server是取的名字,以后在push或pull中可以直接引用。
5、《git-http-backend - Server side implementation of Git over HTTP》:这个描述了如何配置apache来实现http协议的clone和push。我理解的是要用git-http-backend来支持push,一般网上装的gitweb都只提供浏览。
需要记录的是:
- 其中有三行配置,需要修改/etc/apache2/conf-available/gitweb.conf,下面是我的gitweb.conf,其中行1与行2互斥。保留第一行则使用了gitweb,在浏览器http://server/mygit/路径中可以浏览所有项目,但无法clone、push,保留第二行则使用了git-http-backend,而gitweb失效,在浏览器http://server/mygit/中看到的是空白,但可以clone、push。还有行2的路径是lib,而不是原文中的libexec,得自己找,估计跟操作系统有关。
- 另外需要记录的是权限。配置了dav_git.passwd文件并启用之后才能clone,如果不配置权限(注释掉行15、16),clone时报“The requested URL returned error: 403”错误。
- 通过htpasswd命令新增http协议用户,如:htpasswd dav_git.passwd xx增加xx用户。此处是htpasswd命令详解。
- 服务器上项目的文件权限必须配置成777,否则push时会报insufficient permission for adding an object to repository database。
1 #Alias /mygit /usr/share/gitweb 2 ScriptAlias /mygit/ /usr/lib/git-core/git-http-backend/ 3 SetEnv GIT_HTTP_EXPORT_ALL 4 SetEnv GIT_PROJECT_ROOT /var/www/html/repositories 5 6 <Directory /usr/share/gitweb> 7 Options +FollowSymLinks +ExecCGI +SymLinksIfOwnerMatch 8 AddHandler cgi-script .cgi 9 </Directory> 10 11 <Location /mygit/> 12 DAV on 13 AuthType Basic 14 AuthName "My Git" 15 AuthUserFile /etc/apache2/dav_git.passwd 16 Require valid-user 17 </Location>
最后,XCode中远程repositories的地址:http协议:http://server/mygit/test.git。ssh协议:http://ServerIP/mygit/test.git。至于权限,ssh需要填git用户及其密码(server上的git用户在/etc/passwd文件中要/bin/bash,不能/bin/false),http制作passwd文件时的用户名及密码。可能需要在终端窗口中、项目目录下执行git remote add test http://ServerIP/mygit/test.git来为远程服务器命名,后续在xcode中才能进行push。
ps:git clone http://server/mygit/test.git来将服务器的source拉到本地。