
Forgejo Runner
« | 04 Nov 2023 | »Wäre es nicht schön zu wissen, ob der zuletzt hochgeladene Code auch korrekt
gebaut werden kann?
Dafür haben wir CI/CD Features und
Build-Agents auf unterschiedlichen Plattformen.
Codeberg bietet dafür sein Woodpecker CI an … doch etwas versteckt findet man auch Github Actions als forgejo Workflows.
Über Github actions
kann der Server bei einem Ereignis (wie:
“Neuer Code eingecheckt.”) einem registrierten “Runner” auftragen, ein
Script auszuführen.
Und wenn dieses Script dann den neuen Code kompiliert, dann haben wir bereits einen Buildserver aufgesetzt.
Wieder ein neues YAML
Was mich an allen CI/CD Lösungen ankotzt sind deren Uneinigkeit, wie man einen
Vorgang einheitlich abbilden kann. Jede f*cking Lösung erkennt, dass YAML
super geeignet ist für diesen Job … und jede f*cking Lösung löst es ein
bisschen anders.
Gerade so, dass man noch abstrakt erkennt, dass alle Lösungen eigentlich gleich
aufgebaut sind, aber unterschiedlich genug, dass man jede Variante separat
implementieren muss und ja kein Zeichen von A nach B kopieren kann.
… aber gut … genug gelästert.
Meine action-workflows liegen in der Datei /.gitea/workflows/build-platform.yml
und sind etwa so aufgebaut:
1on: [push] 2jobs: 3 build-linux-x64: 4 runs-on: docker 5 container: opendockergate/gate-build-env:deb.10.gcc.8.1 6 steps: 7 - name: checkout sources 8 uses: actions/checkout@v3 9 with: 10 submodules: true 11 - name: run linux GCC X64 build scripts 12 run: | 13 env | sort 14 cd scripts 15 ./build-make.sh 16 cd .. 17 mkdir -p ./dist/linux_x64 18 cp -r ./build/make/deploy/bin/* ./dist/linux_x64 19 ls -l ./dist/linux_x64 20 - name: compress artifacts 21 run: | 22 tar -cJvf artifacts-linux-x64.tar.xz -C ./dist/ . 23 - name: upload artifacts 24 uses: actions/upload-artifact@v3 25 with: 26 name: artifacts-linux-x64.tar.xz 27 path: artifacts-linux-x64.tar.xz 28 retention-days: 7
Man definiert also, dass bei einem push
was passieren soll, und zwar wird der
Job build-linux-x64
gestartet, der auf einem Runner läuft, den man unter dem Tag
docker
findet, und der soll den Container
opendockergate/gate-build-env:deb.10.gcc.8.1
benutzen (also mein Dockerhub Repo).
Jetzt braucht man etwas Detailwissen. Man könnte sich jetzt gleich ein Shell-Script
schreiben, das per GIT alles auscheckt und dann baut, doch dafür gibt es bereits
fertigen Code, der das fehlertolerant abwickelt.
Man muss nur wissen, dass unter dem Namen actions/checkout@v3
ein GIT-Clone
implementiert ist, und dass sich hinter actions/upload-artifact@v3
die HTTP
API zum Hochladen von Build-Ergebnissen zum Forgejo/Codeberg Server verbirgt.
Denn diese Codes werten das Gewirr von Umgebungsvariablen aus und setzen die notwendigen Aktionen um mit wenig Einstellung zum Ziel zu kommen.
In der Mitte befindet sich dann unter run
“mein Buildcode”, der im geklonten
Repository die nötigen Schritte setzt, damit die Sourcen gebaut werden.
Docker Image brauch nodejs
Damit actions
scripts wie checkout
oder upload-artifact
funktionieren,
brauch das Docker image zwingend nodejs
installiert.
Ein Basis Build-Image für C++ unter Codeberg Actions fängt bei mir also so
im Dockerfile
an:
1apt-get install build-essential cmake git nodejs apt-transport-https ca-certificates
Ohne nodejs
treten jede Menge Fehler auf, die nicht unmittelbar auf die
fehlende Node-Installation hinweisen.
Einen Runner braucht man auch
Der forgejo-runner
ist ein kleiner Dienst, den man sich von der Github
Release-Seite herunterladen und auf einer gängigen Linux-Distro mit
Docker-Setup installieren kann.
Zuerst setze ich also eine neue Debian
Maschine auf und installiere
Docker
darauf:
1sudo apt update 2sudo apt upgrade -y 3sudo apt install -y ca-certificates curl 4sudo install -m 0755 -d /etc/apt/keyrings 5sudo curl -fsSL https://download.docker.com/linux/debian/gpg -o /etc/apt/keyrings/docker.asc 6sudo chmod a+r /etc/apt/keyrings/docker.asc 7echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/debian $(. /etc/os-release && echo $VERSION_CODENAME) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null 8sudo apt update 9sudo apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin 10sudo systemctl start docker
Den forgejo-runner
installiere ich dann in /opt/forgejo
:
Auf Codeberg.org erhält man in den “Actions/Runners” Einstellungen einen Registration-Token.
Diesen TOKEN
nutzt man dann auf der Runner Maschine mit dem register
Kommando und danach erzeugt man noch eine Standard-Konfiguration:
Nun hat man die versteckte Registrierungsdatei .runner
und eine
einsatzbereite Konfigurationsdatei config.yml
im Verzeichnis und kann den
neuen Runner auch schon im WebUI auf codeberg.org sehen.
Weitere Infos findet man dann unter
docs.codeberg.org/ci/actions/.
Damit der Dienst bei jedem Systemstart ausgeführt wird, hilft einem
bei systemd
ein Eintrag wie in
/etc/systemd/system/forgejo-runner.service
Die Kommandos:
lassen den neuen forgejo-runner
Dienst dann im Hintergrund ausführen.
Mein Runner läuft in einer kleinen VM auf meinem Server zu Hause und dieser
fragt stets den Codeberg Server, ob neue Jobs anstehen.
Wenn neuer Code per git commit
ed und gepush
t wird, springt der Runner an,
baut alles und lädt das Ergebnis zum Codeberg Server hoch, wo man es für
einige Tage direkt wieder herunterladen kann.
Hinweis: Es dürfte ein Limit von 10 MB pro Upload gesetzt sein, wer mehr hochlädt bekommt HTTP Fehler zurück.
Ich habe meine Binaries vor dem Upload per
tar -cJvf artifacts.tar.xz -C ./output-dir/ .
komprimieren lassen, um nicht zu schnell in das Limit hineinzulaufen.
Fazit
CI/CD kostenlos und alles mit Open-Source Software.
Wer hätte sich das vor 15 Jahren gedacht?
Zwar weist das Forgejo-Projekt immer auf seinen Alpha-Status hin und dass noch einige Fixes fehlen, bis man sich traut “produktiv” genannt zu werden, doch seitdem ich verstanden habe, wie das Ding funktioniert, liebe ich es.
Ja … es wäre mir lieber, wenn Gitlab, Bitbucket und Github sich auf ein YAML Format hätten einigen können, doch da das Setup so einfach umzusetzen ist, kann jedes GIT-Projekt schnell in ein CI-Projekt umgewandelt werden.
Codeberg und Forgejo beweisen, dass sie es trotz ihres vergleichsweise kleinen Team mit den großen Anbietern aufnehmen können und alle notwendigen modernen Features für ein Softwareprojekt bereitstellen können.