Prywatne repozytoria, code review w zespole, albo po prostu niechęć do trzymania wszystkiego u GitHuba. Powodów, żeby mieć własny serwer Git, jest sporo. Popularne opcje są dwie: GitLab i Gitea.

Postawmy sprawę jasno, GitLab Community Edition to kobyła, która w oficjalnych wymaganiach chce co najmniej 4 GB RAM-u tylko dla siebie. Na typowym Mikrusie się nie zmieści i szkoda czasu na próby.

Gitea robi w gruncie rzeczy to samo: repozytoria, issues, pull requesty, wiki, a nawet CI przez Gitea Actions. Tyle że zadowala się ułamkiem tych zasobów. Dlatego w tym poradniku stawiamy właśnie Giteę. Co więcej, sam jej używam od lat i spełnia swoje zadania, to jest prywatnego, lokalnego repozytorium, świetnie.

Na Mikrusie#

Dedykowanego skryptu do Gitei w NOOBS-ie nie mamy, jest za to skrypt do Dockera. A Giteę i tak najwygodniej uruchomić w kontenerze, więc wychodzi na to samo.

NOOBS-a jeszcze nie masz?

curl -s https://noobs.mikr.us | bash

Instalacja Dockera:

sudo /opt/noobs/scripts/chce_dockera.sh

Możesz od razu przeskoczyć do sekcji Pierwsze uruchomienie. Dalej nie ma już znaczenia, czy Dockera postawił skrypt, czy Ty ręcznie.

Na dowolnym serwerze (Ubuntu/Debian)#

Jeśli nie masz jeszcze Dockera, stawiasz go ręcznie. To dokładnie to samo, co robi skrypt NOOBS-a, tylko rozpisane krok po kroku. Działa na Ubuntu i Debianie:

sudo apt update
sudo apt install -y ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/$(. /etc/os-release && echo "$ID")/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

Repozytorium Dockera. Komenda sama dobierze właściwe repozytorium i nazwę wersji Twojego systemu:

echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/$(. /etc/os-release && echo "$ID") \
  $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
  sudo tee /etc/apt/sources.list.d/docker.list > /dev/null

I sam Docker:

sudo apt update
sudo apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

Mała dygresja, bo w starszych poradnikach wciąż są opisane te dwa sposoby: dziś piszemy docker compose, ze spacją. docker-compose z myślnikiem to stara, wycofana wersja.

Pierwsze uruchomienie#

Tworzymy katalog na dane Gitei i plik docker-compose.yml:

mkdir -p ~/gitea && cd ~/gitea
nano docker-compose.yml

Wklejasz:

services:
  gitea:
    image: gitea/gitea:latest
    container_name: gitea
    environment:
      - USER_UID=1000
      - USER_GID=1000
    restart: unless-stopped
    volumes:
      - ./data:/data
      - /etc/timezone:/etc/timezone:ro
      - /etc/localtime:/etc/localtime:ro
    ports:
      - "20112:3000"
      - "30112:22"

Zamiast 20112 i 30112 wpisz dwa ze swoich portów. Standardowo dostajesz trzy: 10000+ID, 20000+ID i 30000+ID. Ten pierwszy zostaw w spokoju, bo to SSH do samego kontenera. Pierwszy port z pliku to panel webowy Gitei, drugi to SSH dla git clone i git push.

Start:

docker compose up -d

Czy kontener żyje?

docker ps

Wchodzisz w przeglądarce pod http://adres-twojego-mikrusa:20112 (czyli port z Twojego docker-compose.yml) i dokańczasz instalację. Gitea sama przeprowadzi Cię przez zakładanie konta administratora. Domyślna baza, czyli wbudowany SQLite, na małym serwerze wystarczy w zupełności. Żadnego osobnego MySQL-a stawiać nie trzeba.

W formularzu instalacyjnym jest jedno pole, które łatwo przeoczyć: “SSH Server Port”. Wpisz tam ten sam port, który w docker-compose.yml podałeś jako drugi (w przykładzie 30112). Dzięki temu komendy git clone, które Gitea podpowiada, od razu będą miały właściwy port.

Podłączenie domeny#

Adres z numerem portu działa, ale nie wygląda zbyt ładnie. Chcesz Giteę pod własną domeną? Najprościej postawić przed nią reverse proxy. Na Mikrusie najszybciej przez Cytrusa z panelu, a ręcznie przez nginx, tak jak w poradniku o reverse proxy na nginx.

Giteę wystawiasz wtedy na porcie 3000 wyłącznie lokalnie ("127.0.0.1:3000:3000" zamiast "20112:3000"), a ruch z domeny przekazuje do niej reverse proxy.

Kopia zapasowa#

Wszystko, co ważne - repozytoria, baza, konfiguracja - leży w katalogu ./data obok docker-compose.yml. Backup sprowadza się więc do spakowania tego katalogu:

cd ~/gitea
docker compose stop
tar -czf gitea-backup-$(date +%Y%m%d).tar.gz data
docker compose start

Zatrzymywanie kontenera nie jest tu fanaberią, a koniecznością. Kopiowanie pracującej bazy SQLite “na żywo” potrafi skończyć się uszkodzonym plikiem, a o tym przekonasz się dopiero wtedy, gdy będziesz go potrzebować.

Najczęstsze błędy#

Port z docker-compose.yml już zajęty. Jeśli na tym Mikrusie na którymś ze standardowych portów stoi już coś innego, docker compose up -d odpowie port is already allocated. Weź inny port ze swojej puli albo dokup kolejny w panelu.

Connection refused na porcie SSH Gitei (30112). To nie błąd. Ten port gada wyłącznie po SSH (git clone), a nie po HTTP. Panel webowy jest pod pierwszym portem, w tym przykładzie: 20112.

git push pyta o hasło, zamiast użyć klucza SSH. Sprawdź dwie rzeczy. Czy Twój klucz publiczny jest dodany w Gitei (Ustawienia → Klucze SSH/GPG). I czy URL repozytorium ma poprawny port SSH (ssh://git@adres:30112/...), a nie domyślny 22.