Since everything is going downhill on the internet,
I spent some time mirroring some of my git repositories on a machine at home.
I chose cgit for the interface, as
everything else is fucking terrible at best. The deployment is trivial: install
cgit and fastcgi, create a git user with /src/git as home, slap the
following into your nginx configuration and you're good to go:
server {
server_name git.dustri.org;
root /usr/share/webapps/cgit;
try_files $uri @cgit;
location ~* ^.+\.(css|png|ico)$ {
root /usr/share/webapps/cgit;
expires 30d;
}
location @cgit {
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root/cgit.cgi;
fastcgi_param PATH_INFO $uri;
fastcgi_param QUERY_STRING $args;
fastcgi_pass unix:/var/run/fcgiwrap/fcgiwrap.sock;
}
}
The configuration for cgit is
also super-simple:
virtual-root=/
scan-path=/srv/git
clone-prefix=https://git.dustri.org
footer=""
section-from-path=1
repository-sort=age
I git clone'd the repositories I wanted to mirror into /srv/git via git
clone --mirror …, and wrote a shell script to kept them updated:
#!/bin/sh
for dir in /srv/git/*/; do
echo "[+] Updating $dir"
git --git-dir="$dir" remote update
touch -d "$(git --git-dir="$dir" --no-pager log -1 --format='%as')" "$dir/packed-refs"
done
As cgit is using packed-refs to determine the last time a git repository
was updated, I set its modification date to the latest's commit one. Using
--format=%ai would be better (ISO
8601), but busybox' touch doesn't
support it, so %as (YYYY-MM-DD) has to suffice. The script is called via the
git's user crontab every day.
For private repositories on github, I generated a per-repo personal access
token
and cloned each of them via git clone --mirror https://jvoisin:github_pat_…@github.com/jvoisin/my_secret_repo.
Preventing them from being listed on the web interface is done by putting a
cgitrc file with hide=1 or ignore=1 at their root depending of what you
prefer.
You can see the result on git.dustri.org.