Forgejo na VPS: własny serwer Git w Dockerze z SSH i kopiami
Forgejo w Dockerze za nginx z HTTPS, klonowanie przez SSH na osobnym porcie, wyłączona rejestracja, kopie danych, runner CI w skrócie i kiedy wystarczy GitHub.
Redakcja serwisu Dealownia · ceny i fakty ze stron dostawców, jak sprawdzamy
Własny serwer Git na Forgejo pod adresem https://git.example.pl: z interfejsem jak w GitHubie (repozytoria, zgłoszenia, pull requesty), z klonowaniem przez HTTPS i przez SSH, z zamkniętą rejestracją i z nocną kopią, z której odtworzysz całą instancję. Forgejo to wolne oprogramowanie rozwijane przez społeczność, odgałęzienie Gitei. Na końcu krótko o runnerze CI i o tym, kiedy darmowy GitHub w zupełności wystarczy.
Czego potrzebujesz
- VPS z Ubuntu 24.04 LTS albo Debianem 12 lub 13, przygotowany jak w poradniku od zera: użytkownik z sudo, ufw, nginx na hoście, certbot, Docker z wtyczką Compose.
- Rozmiar serwera: dokumentacja Forgejo nie podaje minimalnych wymagań sprzętowych. Forgejo to jeden program w Go, a w tym poradniku używa wbudowanej bazy SQLite, więc dla jednej osoby lub małego zespołu zacznij od najmniejszego planu z dyskiem, który pomieści repozytoria, i obserwuj zużycie w
docker stats. Więcej zasobów potrzeba przy dużych repozytoriach, wielu użytkownikach i własnym CI na tym samym serwerze. - Subdomenę
git.example.plz rekordem A wskazującym serwer.
Jeśli chcesz porównać plany pod kątem dysku, zajrzyj do rankingu VPS.
Krok 1. Katalog i compose.yaml
Instrukcja instalacji w Dockerze używa obrazu codeberg.org/forgejo/forgejo z tagiem wersji głównej (obecnie 17, który śledzi najnowsze wydanie poprawkowe). Katalog z danymi musi należeć do UID i GID podanych w USER_UID i USER_GID, inaczej kontener może nie wystartować:
Plik compose.yaml:
Co tu jest ważne:
- Zmienne w formacie
FORGEJO__sekcja__KLUCZnadpisują ustawienia z plikuapp.ini. Pełną listę kluczy i ich wartości domyślnych znajdziesz w ściągawce konfiguracji. ROOT_URLto publiczny adres. Bez niego Forgejo składa adres z protokołu, domeny i portu 3000, więc linki w mailach i adresy klonowania wskazywałybyhttp://...:3000.SSH_PORT=222zmienia tylko port pokazywany w adresie klonowania. Kontener nadal słucha na 22, a Docker przekierowuje na niego port 222 hosta. Port 22 hosta zostaje dla Twojego zwykłego SSH.DISABLE_REGISTRATION=truesprawia, że konta zakłada tylko administrator. Na publicznym serwerze z otwartą rejestracją szybko pojawią się konta spamerów.- Interfejs WWW publikujemy tylko na
127.0.0.1, na porcie hosta 3002 (w kontenerze nadal 3000; 3000 na hoście zajmuje zwykle Umami) – na zewnątrz wystawi go nginx z HTTPS. Port 222 jest publiczny celowo; pamiętaj, że opublikowane porty Dockera omijają ufw, więc dla tego portu reguła w ufw niczego nie zmienia.
Bez konfiguracji bazy Forgejo używa SQLite. Jeśli spodziewasz się wielu użytkowników, ta sama strona dokumentacji pokazuje wariant z PostgreSQL.
Krok 2. nginx i HTTPS
Konfiguracja według dokumentacji reverse proxy Forgejo, plik /etc/nginx/sites-available/git.example.pl:
merge_slashes off dokumentacja wymaga do obsługi adresów z zakodowanymi ukośnikami, a client_max_body_size 512M pozwala wypchnąć przez HTTPS duże commity i wydania z plikami. Ogólne zasady konfiguracji proxy opisuje poradnik o reverse proxy.
Krok 3. Instalacja i konto administratora
Przy pierwszym wejściu na https://git.example.pl Forgejo pokaże stronę instalacji z polami wypełnionymi wartościami ze zmiennych środowiskowych. Zrób to od razu po uruchomieniu – dopóki instalacja nie jest zakończona, ta strona jest dostępna dla każdego. Sprawdź, czy baza to SQLite, a adres bazowy to https://git.example.pl/, rozwiń sekcję ustawień konta administratora i załóż je tam. Po instalacji Forgejo zapisze INSTALL_LOCK = true w app.ini i strona instalacji przestanie być dostępna.
Kolejne konta założysz w panelu administratora albo z wiersza poleceń (proces w kontenerze działa jako użytkownik git):
Wygenerowane hasło pojawi się w wyniku polecenia – przekaż je osobie bezpiecznym kanałem.
Krok 4. Repozytoria przez SSH
Dodaj swój klucz publiczny w ustawieniach użytkownika (Ustawienia → Klucze SSH/GPG) i sprawdź połączenie:
Forgejo odpowie powitaniem z Twoją nazwą użytkownika – nie da powłoki, i tak ma być. Adres klonowania ma postać:
Żeby nie podawać portu za każdym razem, dopisz na swoim komputerze do ~/.ssh/config:
Wtedy działa też krótka forma git clone git@git.example.pl:ania/projekt.git.
Krok 5. Kopie
Dokumentacja kopii Forgejo zaleca zatrzymanie Forgejo na czas kopii, bo kopia działającej instancji może być niespójna i przy odtwarzaniu stracisz dane. Przy SQLite i domyślnej konfiguracji katalog danych zawiera bazę, repozytoria, załączniki i kolejki, a app.ini z niezastępowalnymi sekretami (SECRET_KEY, JWT_SECRET) leży w nim w gitea/conf/. Wystarczy więc spakować cały katalog ./forgejo. Skrypt /opt/apps/forgejo/backup.sh:
trap … EXIT uruchamia Forgejo z powrotem zawsze, gdy skrypt się kończy – także po błędzie. Stare archiwa są kasowane dopiero po udanym tar: przy błędzie (np. pełny dysk) set -e przerywa skrypt przed find, więc dotychczasowe kopie zostają, a w logu /var/log/forgejo-kopia.log widać błąd. Archiwum powstaje najpierw jako .part, więc niedokończony plik nigdy nie wygląda jak gotowa kopia. umask 077 i katalog 700 sprawiają, że archiwa (z app.ini i jego sekretami) czyta tylko root. Na wszelki wypadek sprawdzaj czasem rozmiar archiwów. Przerwa trwa tyle, ile pakowanie – przy kilku gigabajtach repozytoriów to zwykle chwila. Archiwa wysyłaj poza serwer, np. jak w poradniku o restic i rclone. Przed aktualizacją do nowej wersji głównej (zmiana tagu, np. z 17 na 18) dokumentacja aktualizacji wymaga pełnej kopii.
Runner CI w skrócie
Forgejo Actions jest domyślnie włączone i używa składni bardzo podobnej do GitHub Actions. Zadania nie wykonuje jednak sam serwer, tylko osobny program Forgejo Runner (obraz data.forgejo.org/forgejo/runner). Rejestrujesz go w panelu administratora pod /admin/actions/runners przyciskiem tworzenia nowego runnera, który pokaże jednorazowy sekret do pliku konfiguracyjnego runnera. Szczegóły instalacji są w dokumentacji Actions.
Dokumentacja ostrzega, że runner wykonuje zdalny kod, co jest poważnym zagrożeniem dla maszyny i sieci, na której działa. Dlatego nie stawiaj go na tym samym VPS co Forgejo, jeśli do repozytoriów mają dostęp inne osoby – osobny mały serwer albo maszyna wirtualna ograniczają skutki złośliwego workflowu.
Kiedy wystarczy darmowy GitHub
GitHub Free daje nielimitowane repozytoria publiczne i prywatne oraz 2000 minut CI miesięcznie (szczegóły na stronie darmowe). Jeśli pracujesz sam albo w małym zespole, nie masz wymogu trzymania kodu u siebie i mieścisz się w minutach CI, własny serwer doda Ci tylko obowiązków: aktualizacje, kopie, monitoring. Forgejo ma sens, gdy kod nie może opuścić Twojej infrastruktury, chcesz uniezależnić się od jednej firmy, potrzebujesz kopii lustrzanych wielu repozytoriów albo masz już VPS i chcesz CI bez limitu minut.
Najczęstsze problemy
- Kontener restartuje się z błędem uprawnień do
/data. Katalog./forgejonie należy do UID 1000. Popraw:sudo chown -R 1000:1000 /opt/apps/forgejo/forgejo. - Adres klonowania pokazuje
localhost:3000albohttp://. BrakROOT_URLw zmiennych albo wcześniej zapisana wartość wapp.ini. Sprawdźdocker exec forgejo grep -A3 '^\[server\]' /data/gitea/conf/app.inii zrestartuj kontener. git pushprzez SSH pyta o hasło albo zwracaPermission denied (publickey). Łączysz się na port 22 hosta zamiast 222. Sprawdźssh -T -p 222 git@git.example.pli wpis w~/.ssh/config.- SSH na 222 nie działa, gdy domena stoi za Cloudflare. Proxy Cloudflare przepuszcza tylko HTTP i HTTPS. Dla SSH ustaw osobny rekord bez proxy, np.
ssh.git.example.pl, i podaj go wSSH_DOMAIN– więcej w poradniku o Cloudflare. - Wypchnięcie dużego repozytorium przez HTTPS kończy się błędem 413. Za mały
client_max_body_sizew bloku HTTPS po certbocie – sprawdźsudo nginx -T | grep client_max_body_size.
Co dalej
Dodaj monitoring adresu w Uptime Kuma i przejdź listę kontrolną zabezpieczeń. Jeśli na tym samym serwerze stoją inne narzędzia, uporządkuj je jak w stacku w jednym pliku compose.