With the advent of GitLab 8.0 and gitlab-git-http-server, it became slightly more difficult to run it using Passenger. These are my notes on the caveats.

Update (7.10.2015) gitlab-git-http-server has switched from sending a custom User-Agent to sending a special header in version 0.9.14. User-Agent is now forwarded from the client request. I've updated the last section accordingly.

Install GitLab from Source

Just follow the official installation instructions, but skip installing the init script /etc/init.d/gitlab and the chapter about nginx.

Start sidekiq and gitlab-git-http-server

Because we are not using the official init scripts, we will have to make sure the services not provided by Passenger are running. If you use a systemd-based distro such as Debian jessie, you can find service files for both sidekiq and gitlab-git-http-server in the GitLab Recipes repository. Because Apache's mod_proxy has some problems with unix domain sockets, you will have to modify the arguments for gitlab-git-http-server so it listens on a port (I will use 8181 in this guide). We will also use your main GitLab domain as authBackend, because GitLab is running inside Passenger and we don't have a separate port to connect to (and we'll make sure routing still works in the Apache config).

Here is my systemd service file for the gitlab-git-http-server:

[Unit]
Description=GitLab git-http-server

[Service]
User=git
WorkingDirectory=/home/git/gitlab-git-http-server
ExecStart=/home/git/gitlab-git-http-server/gitlab-git-http-server -listenAddr 127.0.0.1:8181 -authBackend https://your.gitlab.host /home/git/repositories

[Install]
WantedBy=multi-user.target

After you copied both service files to /etc/systemd/system, just enable and start them as usual:

$ systemctl enable gitlab-sidekiq.service
$ systemctl enable gitlab-githttpserver.service
$ systemctl start gitlab-sidekiq.service
$ systemctl start gitlab-githttpserver.service

Configure proxying for Apache

I'll assume you already have Apache and Passenger running. In your usual vhost config, just set DocumentRoot "/home/git/gitlab/public/" and then add the following:

# Ensure that encoded slashes don't result in a 404 but are passed encoded
# to the app.
# https://httpd.apache.org/docs/2.4/en/mod/core.html#allowencodedslashes
AllowEncodedSlashes NoDecode

# Don't rewrite the Host header. Needed to not confuse gitlab-git-http-server
# Also without this SNI will break, because gitlab-git-http-server reflects the
# Host header it receives back at us
ProxyPreserveHost on

# Allow reverse-proxying to gitlab-git-http-server
<Location />
  ProxyPassReverse http://127.0.0.1:8181
</Location>

# Forward access to git repos, but only from users, because
# gitlab-git-http-server queries gitlab for auth info like this
RewriteEngine on
RewriteCond "%{REQUEST_URI}" "^[-/\w\.]+\.git/"
RewriteCond "%{HTTP:GitLab-Git-HTTP-Server}" =""
RewriteRule . http://127.0.0.1:8181%{REQUEST_URI} [P,QSA]

Make sure you are using version 0.2.14 of gitlab-git-http-server or newer for this to work. You can choose another port if 8181 is already taken, just remember to replace it in the systemd service file as well.

Security warning: When you run your GitLab installation like this, your upload folder is not routed through GitLab like it is with the default Nginx config. While all uploads still are still protected by the checksum of their content, anyone with the link can download the file, regardless of permissions. This also results in a risk of XSS (see this issue), but that assumes you have untrusted users on your installation.

Previous Post Next Post