# GerbilManager CI — Gitea Actions # ================================= # STATUS: ENTWURF — inaktiv bis Julian Gitea Actions aktiviert. # Aktivierung: Gitea -> Repository -> Einstellungen -> Actions -> "Actions aktivieren" # Anschliessend: Gitea Actions Runner auf der NAS installieren (siehe docs/ops.md). # # Was dieser Workflow tut: # 1. dotnet test (alle xUnit-Projekte) # 2. npm test + npm run build (Frontend) # 3. Docker-Images bauen und in die Gitea-Registry pushen # # Registry: git.rismer.de (Gitea Container Registry über HTTPS — keine insecure-registry-Konfig nötig) # Images: # git.rismer.de/gulum/gerbilmanager-api:latest # git.rismer.de/gulum/gerbilmanager-frontend:latest name: CI on: push: branches: - main pull_request: branches: - main # Manueller „Run workflow"-Button in Gitea: testet, baut, pusht und deployt frisch. # Fuer einen Rollback auf ein altes Image stattdessen auf der NAS: # TAG= sh /opt/gerbilmanager/deploy/truenas/scripts/deploy.sh workflow_dispatch: env: REGISTRY: git.rismer.de REGISTRY_OWNER: gulum DOTNET_VERSION: "10.0.x" NODE_VERSION: "22" jobs: test-backend: name: Backend Tests (.NET) runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: .NET SDK einrichten uses: actions/setup-dotnet@v4 with: dotnet-version: ${{ env.DOTNET_VERSION }} - name: Pakete wiederherstellen run: dotnet restore GerbilManager.slnx - name: Build run: dotnet build GerbilManager.slnx --no-restore -c Release - name: dotnet-ef Tool installieren # 'tool update' ist idempotent (installiert wenn fehlend, sonst aktualisiert) — # auf dem SELF-HOSTED Runner persistieren --global Tools, daher schlug 'tool install' # ab dem 2. Lauf mit 'already installed' fehl und kippte den Backend-Job. # GITHUB_PATH-Zeile: global tools landen in ~/.dotnet/tools, das auf dem Runner-Container # nicht im PATH ist — einmalig eintragen, damit alle Folge-Steps 'dotnet ef' finden. run: | dotnet tool update --global dotnet-ef --version 10.0.* echo "$HOME/.dotnet/tools" >> $GITHUB_PATH - name: DB-3 EF Migrations Drift-Check # Fails CI if the EF model diverges from the snapshot (i.e. a code change touched # entities/OnModelCreating without generating a matching migration). Catches exactly # the class of drift the SQLite/EnsureCreated test host is blind to. run: > dotnet ef migrations has-pending-model-changes --project GerbilManagerWebAPI --startup-project GerbilManagerWebAPI --no-build --configuration Release - name: Tests ausfuehren run: dotnet test GerbilManager.slnx --no-build -c Release --logger "console;verbosity=normal" test-frontend: name: Frontend Tests (Node/Vite) runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Node.js einrichten uses: actions/setup-node@v4 with: node-version: ${{ env.NODE_VERSION }} cache: "npm" cache-dependency-path: gerbil-manager-web/package-lock.json - name: Abhaengigkeiten installieren run: npm ci working-directory: gerbil-manager-web - name: Tests ausfuehren run: npm test working-directory: gerbil-manager-web - name: Produktionsbuild pruefen run: npm run build working-directory: gerbil-manager-web build-and-push: name: Docker Build & Push runs-on: ubuntu-latest needs: [test-backend, test-frontend] if: github.ref == 'refs/heads/main' && (github.event_name == 'push' || github.event_name == 'workflow_dispatch') steps: - uses: actions/checkout@v4 - name: Bei Gitea Registry anmelden uses: docker/login-action@v3 with: registry: ${{ env.REGISTRY }} username: ${{ secrets.REGISTRY_USER }} password: ${{ secrets.REGISTRY_TOKEN }} - name: Docker Buildx einrichten uses: docker/setup-buildx-action@v3 - name: API-Image bauen und pushen uses: docker/build-push-action@v5 with: context: . file: GerbilManagerWebAPI/Dockerfile push: true tags: | ${{ env.REGISTRY }}/${{ env.REGISTRY_OWNER }}/gerbilmanager-api:latest ${{ env.REGISTRY }}/${{ env.REGISTRY_OWNER }}/gerbilmanager-api:${{ github.sha }} - name: Frontend-Image bauen und pushen uses: docker/build-push-action@v5 with: context: . file: gerbil-manager-web/Dockerfile push: true tags: | ${{ env.REGISTRY }}/${{ env.REGISTRY_OWNER }}/gerbilmanager-frontend:latest ${{ env.REGISTRY }}/${{ env.REGISTRY_OWNER }}/gerbilmanager-frontend:${{ github.sha }} deploy: name: Deploy auf TrueNAS (Custom App) # Laeuft auf dem vorhandenen containerisierten Gitea-Runner (Label ubuntu-latest). # Der Runner hat KEINEN Host-Dateisystem-/midclt-Zugriff, daher: per SSH zum NAS-Host # verbinden, die Deploy-Dateien in das App-Home auf dem Pool kopieren und dort # truenas-deploy.sh ausfuehren (legt die TrueNAS "Custom App" an bzw. rollt sie neu # aus via `midclt` — die App bleibt unter Apps sichtbar). # Hinweis: / (inkl. /opt) ist auf TrueNAS Goldeye read-only -> App-Home auf dem Pool. # # Benoetigte Repo-Secrets (Gitea -> Einstellungen -> Actions -> Secrets): # NAS_SSH_HOST z. B. 192.168.2.115 (Host-LAN-IP der NAS) # NAS_SSH_KEY privater SSH-Deploy-Key (Pubkey liegt in /root/.ssh/authorized_keys) runs-on: ubuntu-latest needs: [build-and-push] if: github.ref == 'refs/heads/main' && (github.event_name == 'push' || github.event_name == 'workflow_dispatch') env: APP_HOME: /mnt/JailStorage/DockerVolumes/gerbilmanager steps: - uses: actions/checkout@v4 - name: SSH-Client + Key einrichten run: | command -v ssh >/dev/null 2>&1 || (apt-get update && apt-get install -y --no-install-recommends openssh-client rsync) install -m 700 -d ~/.ssh printf '%s\n' "${{ secrets.NAS_SSH_KEY }}" > ~/.ssh/id_deploy chmod 600 ~/.ssh/id_deploy ssh-keyscan -H "${{ secrets.NAS_SSH_HOST }}" >> ~/.ssh/known_hosts 2>/dev/null || true - name: Deploy-Dateien auf den NAS-Host kopieren run: | NAS="root@${{ secrets.NAS_SSH_HOST }}" SSH="ssh -i ~/.ssh/id_deploy -o StrictHostKeyChecking=accept-new" $SSH "$NAS" "mkdir -p $APP_HOME/deploy/truenas/scripts" rsync -az -e "$SSH" \ deploy/truenas/custom-app.compose.yaml \ "$NAS":"$APP_HOME"/deploy/truenas/ rsync -az -e "$SSH" \ deploy/truenas/scripts/ \ "$NAS":"$APP_HOME"/deploy/truenas/scripts/ - name: Custom App neu ausrollen (midclt create/redeploy + Health-Check) run: | NAS="root@${{ secrets.NAS_SSH_HOST }}" ssh -i ~/.ssh/id_deploy -o StrictHostKeyChecking=accept-new "$NAS" \ "sh $APP_HOME/deploy/truenas/scripts/truenas-deploy.sh"