chore(ci): Align GH Workflows with Docker SSoT, new paths; minimal SSoT guard; staticAnalysis (#23)

* chore(MP-21): snapshot pre-refactor state (Epic 1)

* chore(MP-22): scaffold new repo structure, relocate Docker Compose, move frontend/backend modules, update Makefile; add docs mapping and env template

* MP-22 Epic 2: Erfolgreich umgesetzt und verifiziert

* MP-23 Epic 3: Gradle/Build Governance zentralisieren

* MP-23 Epic 3: Gradle/Build Governance zentralisieren

* chore(devops)!: Docker-SSoT (.env) konsolidiert, Compose-Mounts ergänzt, Makefile entfernt

- ENV Single Source of Truth
  - docker/.env.example neu (inkl. REDIS_PASSWORD, Ports, Build-Overrides)
  - config/.env(.example) als DEPRECATED markiert (Verweis auf docker/.env[.example])

- Docker Compose vereinheitlicht (docker/docker-compose.yaml)
  - Postgres: zentralen postgresql.conf mounten (../config/postgres/postgresql.conf)
    und Start mit -c config_file=/etc/postgresql/postgresql.conf
  - Redis: zentralen redis.conf mounten (../config/redis/redis.conf)
    und Start via "redis-server … ${REDIS_PASSWORD:+--requirepass $REDIS_PASSWORD}"
  - Web-Nginx: ../config/nginx/nginx.prod.conf → /etc/nginx/nginx.conf (ro)
  - Monitoring: Prometheus/Grafana nutzen ../config/monitoring/* als SSoT

- Frontend/DI/Network (MP-23 Grundlage)
  - :frontend:core:network Modul mit Koin `apiClient` (Ktor + JSON/Retry/Timeout/Logging)
  - Plattform-Basis-URL-Auflösung (JVM: ENV API_BASE_URL; JS: globalThis.API_BASE_URL / Same-Origin)
  - Web index.html setzt API_BASE_URL (Query `?apiBaseUrl=…` > Same-Origin > Fallback)

- Build/Gradle & Module-Refs
  - settings.gradle.kts: neue Frontend-/Backend-Pfade bereits inkludiert
  - Features/Shell: Abhängigkeiten auf :frontend:shared / :frontend:core:* angepasst
  - Ping-API-Refs auf :backend:services:ping:ping-api vereinheitlicht

- Dockerfiles angepasst
  - backend/infrastructure/gateway/Dockerfile → Tasks/Pfade auf :backend:gateway
  - backend/services/ping/Dockerfile → Tasks/Pfade auf :backend:services:ping:ping-service

- Static Analysis / Guards
  - config/detekt/detekt.yml hinzugefügt
  - Leichter Arch-Guard (Frontend) gegen manuelle Authorization-Header vorbereitet

- Doku
  - docs/ARCHITECTURE.md (Struktur, Mapping, Next Steps) ergänzt
  - docs/adr/README.md angelegt

BREAKING CHANGES:
- Makefile komplett entfernt (bitte direkt `docker compose` verwenden)
- ENV-Quelle ist jetzt docker/.env (statt config/.env oder Root)
- Compose-Datei unter docker/docker-compose.yaml (nicht mehr compose.yaml im Repo-Root)

Verifikation (lokal):
- ENV anlegen: `cp docker/.env.example docker/.env` (Werte anpassen)
- Compose prüfen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml config`
- Infrastruktur: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle up -d postgres redis keycloak web-app`
- Services bauen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle build api-gateway ping-service --no-cache --progress=plain`

Refs: MP-22 (Epic 2), MP-23 (Epic 3)

* chore(devops)!: Docker-SSoT (.env) konsolidiert, Compose-Mounts ergänzt, Makefile entfernt

- ENV Single Source of Truth
  - docker/.env.example neu (inkl. REDIS_PASSWORD, Ports, Build-Overrides)
  - config/.env(.example) als DEPRECATED markiert (Verweis auf docker/.env[.example])

- Docker Compose vereinheitlicht (docker/docker-compose.yaml)
  - Postgres: zentralen postgresql.conf mounten (../config/postgres/postgresql.conf)
    und Start mit -c config_file=/etc/postgresql/postgresql.conf
  - Redis: zentralen redis.conf mounten (../config/redis/redis.conf)
    und Start via "redis-server … ${REDIS_PASSWORD:+--requirepass $REDIS_PASSWORD}"
  - Web-Nginx: ../config/nginx/nginx.prod.conf → /etc/nginx/nginx.conf (ro)
  - Monitoring: Prometheus/Grafana nutzen ../config/monitoring/* als SSoT

- Frontend/DI/Network (MP-23 Grundlage)
  - :frontend:core:network Modul mit Koin `apiClient` (Ktor + JSON/Retry/Timeout/Logging)
  - Plattform-Basis-URL-Auflösung (JVM: ENV API_BASE_URL; JS: globalThis.API_BASE_URL / Same-Origin)
  - Web index.html setzt API_BASE_URL (Query `?apiBaseUrl=…` > Same-Origin > Fallback)

- Build/Gradle & Module-Refs
  - settings.gradle.kts: neue Frontend-/Backend-Pfade bereits inkludiert
  - Features/Shell: Abhängigkeiten auf :frontend:shared / :frontend:core:* angepasst
  - Ping-API-Refs auf :backend:services:ping:ping-api vereinheitlicht

- Dockerfiles angepasst
  - backend/infrastructure/gateway/Dockerfile → Tasks/Pfade auf :backend:gateway
  - backend/services/ping/Dockerfile → Tasks/Pfade auf :backend:services:ping:ping-service

- Static Analysis / Guards
  - config/detekt/detekt.yml hinzugefügt
  - Leichter Arch-Guard (Frontend) gegen manuelle Authorization-Header vorbereitet

- Doku
  - docs/ARCHITECTURE.md (Struktur, Mapping, Next Steps) ergänzt
  - docs/adr/README.md angelegt

BREAKING CHANGES:
- Makefile komplett entfernt (bitte direkt `docker compose` verwenden)
- ENV-Quelle ist jetzt docker/.env (statt config/.env oder Root)
- Compose-Datei unter docker/docker-compose.yaml (nicht mehr compose.yaml im Repo-Root)

Verifikation (lokal):
- ENV anlegen: `cp docker/.env.example docker/.env` (Werte anpassen)
- Compose prüfen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml config`
- Infrastruktur: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle up -d postgres redis keycloak web-app`
- Services bauen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle build api-gateway ping-service --no-cache --progress=plain`

Refs: MP-22 (Epic 2), MP-23 (Epic 3)

* chore(devops)!: Docker-SSoT (.env) konsolidiert, Compose-Mounts ergänzt, Makefile entfernt

- ENV Single Source of Truth
  - docker/.env.example neu (inkl. REDIS_PASSWORD, Ports, Build-Overrides)
  - config/.env(.example) als DEPRECATED markiert (Verweis auf docker/.env[.example])

- Docker Compose vereinheitlicht (docker/docker-compose.yaml)
  - Postgres: zentralen postgresql.conf mounten (../config/postgres/postgresql.conf)
    und Start mit -c config_file=/etc/postgresql/postgresql.conf
  - Redis: zentralen redis.conf mounten (../config/redis/redis.conf)
    und Start via "redis-server … ${REDIS_PASSWORD:+--requirepass $REDIS_PASSWORD}"
  - Web-Nginx: ../config/nginx/nginx.prod.conf → /etc/nginx/nginx.conf (ro)
  - Monitoring: Prometheus/Grafana nutzen ../config/monitoring/* als SSoT

- Frontend/DI/Network (MP-23 Grundlage)
  - :frontend:core:network Modul mit Koin `apiClient` (Ktor + JSON/Retry/Timeout/Logging)
  - Plattform-Basis-URL-Auflösung (JVM: ENV API_BASE_URL; JS: globalThis.API_BASE_URL / Same-Origin)
  - Web index.html setzt API_BASE_URL (Query `?apiBaseUrl=…` > Same-Origin > Fallback)

- Build/Gradle & Module-Refs
  - settings.gradle.kts: neue Frontend-/Backend-Pfade bereits inkludiert
  - Features/Shell: Abhängigkeiten auf :frontend:shared / :frontend:core:* angepasst
  - Ping-API-Refs auf :backend:services:ping:ping-api vereinheitlicht

- Dockerfiles angepasst
  - backend/infrastructure/gateway/Dockerfile → Tasks/Pfade auf :backend:gateway
  - backend/services/ping/Dockerfile → Tasks/Pfade auf :backend:services:ping:ping-service

- Static Analysis / Guards
  - config/detekt/detekt.yml hinzugefügt
  - Leichter Arch-Guard (Frontend) gegen manuelle Authorization-Header vorbereitet

- Doku
  - docs/ARCHITECTURE.md (Struktur, Mapping, Next Steps) ergänzt
  - docs/adr/README.md angelegt

BREAKING CHANGES:
- Makefile komplett entfernt (bitte direkt `docker compose` verwenden)
- ENV-Quelle ist jetzt docker/.env (statt config/.env oder Root)
- Compose-Datei unter docker/docker-compose.yaml (nicht mehr compose.yaml im Repo-Root)

Verifikation (lokal):
- ENV anlegen: `cp docker/.env.example docker/.env` (Werte anpassen)
- Compose prüfen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml config`
- Infrastruktur: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle up -d postgres redis keycloak web-app`
- Services bauen: `docker compose --env-file docker/.env -f docker/docker-compose.yaml -p meldestelle build api-gateway ping-service --no-cache --progress=plain`

Refs: MP-22 (Epic 2), MP-23 (Epic 3)

* chore(ci): Workflows an Docker-SSoT & neue Struktur angepasst, minimaler SSoT-Guard

- ssot-guard.yml: Option B (minimal) → `docker compose -f docker/docker-compose.yaml config` als Lint
- integration-tests.yml: `./gradlew staticAnalysis` vor Integrationstests
- docs-kdoc-sync.yml: Dokka-Task Fallback (dokkaGfmAll || dokkaGfm), YouTrack-Sync nur wenn Script vorhanden
- deploy-proxmox.yml: Compose-Pfade auf docker/docker-compose.yaml + `--env-file docker/.env`; Build/Test Schritte vereinheitlicht
- ci-main.yml: SSoT-Skripte per `if: hashFiles(...)` guarded, Compose-Lint Fallback; OpenAPI‑Pfad → backend/gateway; ADR‑Pfade → docs/adr/**; `staticAnalysis` in Build integriert
- youtrack-sync.yml: unverändert (funktional)

Refs: MP-22, MP-23

* chore(ci): Workflows an Docker-SSoT & neue Struktur angepasst, minimaler SSoT-Guard

- ssot-guard.yml: Option B (minimal) → `docker compose -f docker/docker-compose.yaml config` als Lint
- integration-tests.yml: `./gradlew staticAnalysis` vor Integrationstests
- docs-kdoc-sync.yml: Dokka-Task Fallback (dokkaGfmAll || dokkaGfm), YouTrack-Sync nur wenn Script vorhanden
- deploy-proxmox.yml: Compose-Pfade auf docker/docker-compose.yaml + `--env-file docker/.env`; Build/Test Schritte vereinheitlicht
- ci-main.yml: SSoT-Skripte per `if: hashFiles(...)` guarded, Compose-Lint Fallback; OpenAPI‑Pfad → backend/gateway; ADR‑Pfade → docs/adr/**; `staticAnalysis` in Build integriert
- youtrack-sync.yml: unverändert (funktional)

Refs: MP-22, MP-23

* fix(ci): create .env from example before validating compose config

* fix(ci): update ssot-guard filename (.yaml) and sync workflow state

* fixing

* fix(webpack): correct sql.js fallback configuration for webpack 5
This commit is contained in:
StefanMo
2025-12-03 12:03:40 +01:00
committed by GitHub
parent 034892e890
commit 95fe3e0573
365 changed files with 2283 additions and 15142 deletions
+16 -10
View File
@@ -21,19 +21,25 @@ jobs:
name: Docker SSoT Validation
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: actions/checkout@v6
- name: Validate Docker SSoT (compat mode)
if: ${{ hashFiles('scripts/docker-versions-update.sh') != '' && hashFiles('scripts/generate-compose-files.sh') != '' && hashFiles('scripts/validate-docker-consistency.sh') != '' }}
run: |
bash scripts/docker-versions-update.sh sync
bash scripts/generate-compose-files.sh all development
bash scripts/validate-docker-consistency.sh all
- name: Validate Docker SSoT (envless mode)
if: ${{ hashFiles('scripts/generate-compose-files.sh') != '' && hashFiles('scripts/validate-docker-consistency.sh') != '' }}
run: |
DOCKER_SSOT_MODE=envless bash scripts/generate-compose-files.sh all development
DOCKER_SSOT_MODE=envless bash scripts/validate-docker-consistency.sh all
- name: Lint docker-compose (fallback)
if: ${{ hashFiles('scripts/validate-docker-consistency.sh') == '' }}
run: docker compose -f docker/docker-compose.yaml config
# ========================================
# 2. OpenAPI Validation (nur Lint)
# ========================================
@@ -41,10 +47,10 @@ jobs:
name: Validate OpenAPI Specs
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: actions/checkout@v6
- name: Setup Node.js
uses: actions/setup-node@v4
uses: actions/setup-node@v6
with:
node-version: '20'
@@ -53,7 +59,7 @@ jobs:
- name: Validate OpenAPI
run: |
spectral lint infrastructure/gateway/src/main/resources/openapi/documentation.yaml \
spectral lint backend/gateway/src/main/resources/openapi/documentation.yaml \
--ruleset .spectral.yaml \
--fail-severity error
@@ -64,22 +70,22 @@ jobs:
name: Validate Essential Docs
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: actions/checkout@v6
- name: Lint Critical Markdown
uses: DavidAnson/markdownlint-cli2-action@v20
uses: DavidAnson/markdownlint-cli2-action@v21
with:
globs: |
README.md
docs/README.md
docs/architecture/adr/**/*.md
docs/adr/**/*.md
docs/how-to/start-local.md
- name: Check Links in ADRs
uses: gaurav-nelson/github-action-markdown-link-check@v1
with:
config-file: '.github/markdown-link-check.json'
folder-path: 'docs/architecture/adr/'
folder-path: 'docs/adr/'
use-quiet-mode: 'yes'
# ========================================
@@ -91,7 +97,7 @@ jobs:
needs: [ docker-ssot, validate-openapi, validate-docs ]
steps:
- uses: actions/checkout@v5
- uses: actions/checkout@v6
- name: Setup JDK 21
uses: actions/setup-java@v5
@@ -101,7 +107,7 @@ jobs:
cache: gradle
- name: Build
run: ./gradlew build -x test
run: ./gradlew staticAnalysis build -x test
- name: Test
run: ./gradlew test
+18 -15
View File
@@ -27,7 +27,7 @@ jobs:
steps:
- name: Checkout Code
uses: actions/checkout@v5
uses: actions/checkout@v6
- name: Set up JDK 21
uses: actions/setup-java@v5
@@ -48,11 +48,14 @@ jobs:
- name: Grant execute permission for gradlew
run: chmod +x gradlew
- name: Build Client (Test Compilation)
run: ./gradlew :client:compileCommonMainKotlinMetadata --no-daemon
- name: Static Analysis
run: ./gradlew staticAnalysis --no-daemon || true
- name: Run Client Tests
run: ./gradlew :client:test --no-daemon || true # Allow failure for now
- name: Build (all)
run: ./gradlew build -x test --no-daemon
- name: Test (all)
run: ./gradlew test --no-daemon || true # Allow failure for now
# ===================================================================
# Deploy to Proxmox (nur bei main branch)
@@ -64,7 +67,7 @@ jobs:
steps:
- name: Checkout Code
uses: actions/checkout@v5
uses: actions/checkout@v6
- name: Setup SSH Key
uses: webfactory/ssh-agent@v0.8.0
@@ -98,7 +101,7 @@ jobs:
# Stop existing services
echo "🛑 Stopping existing services..."
docker compose -f docker-compose.yml -f docker-compose.services.yml -f docker-compose.clients.yml down || true
docker compose --env-file docker/.env -f docker/docker-compose.yaml down || true
# Clean up old images (optional)
echo "🧹 Cleaning up old images..."
@@ -106,13 +109,11 @@ jobs:
# Build new images
echo "🏗️ Building new images..."
docker compose -f docker-compose.yml build
docker compose -f docker-compose.services.yml build
docker compose -f docker-compose.clients.yml build
docker compose --env-file docker/.env -f docker/docker-compose.yaml build
# Start infrastructure first
echo "🚀 Starting infrastructure..."
docker compose -f docker-compose.yml up -d
docker compose --env-file docker/.env -f docker/docker-compose.yaml up -d
# Wait for infrastructure to be ready
echo "⏳ Waiting for infrastructure..."
@@ -120,7 +121,8 @@ jobs:
# Start services
echo "🚀 Starting services..."
docker compose -f docker-compose.yml -f docker-compose.services.yml up -d
# Start services (already included in main compose file)
docker compose --env-file docker/.env -f docker/docker-compose.yaml up -d
# Wait for services to be ready
echo "⏳ Waiting for services..."
@@ -128,7 +130,8 @@ jobs:
# Start clients
echo "🚀 Starting clients..."
docker compose -f docker-compose.yml -f docker-compose.services.yml -f docker-compose.clients.yml up -d
# Start clients (already included in main compose file)
docker compose --env-file docker/.env -f docker/docker-compose.yaml up -d
# Health check
echo "🏥 Running health checks..."
@@ -136,11 +139,11 @@ jobs:
# Check service status
echo "📊 Service Status:"
docker compose -f docker-compose.yml -f docker-compose.services.yml -f docker-compose.clients.yml ps
docker compose --env-file docker/.env -f docker/docker-compose.yaml ps
# Check logs for errors
echo "📋 Recent logs:"
docker compose -f docker-compose.yml -f docker-compose.services.yml -f docker-compose.clients.yml logs --tail=50
docker compose --env-file docker/.env -f docker/docker-compose.yaml logs --tail=50
echo "✅ Deployment completed successfully!"
ENDSSH
+4 -2
View File
@@ -26,7 +26,7 @@ jobs:
contents: read
steps:
- name: Checkout
uses: actions/checkout@v5
uses: actions/checkout@v6
- name: Setup JDK 21
uses: actions/setup-java@v5
@@ -38,7 +38,8 @@ jobs:
uses: gradle/actions/setup-gradle@v5
- name: Build Dokka (GFM)
run: ./gradlew --no-daemon dokkaGfmAll
run: |
./gradlew --no-daemon dokkaGfmAll || ./gradlew --no-daemon dokkaGfm
- name: Python deps for YouTrack sync
run: |
@@ -46,6 +47,7 @@ jobs:
pip install requests pyyaml
- name: Sync KDoc Markdown to YouTrack KB
if: ${{ hashFiles('.junie/scripts/youtrack-sync-kb.py') != '' }}
env:
YT_URL: ${{ secrets.YT_URL }}
YT_TOKEN: ${{ secrets.YT_TOKEN }}
+4 -1
View File
@@ -93,7 +93,7 @@ jobs:
--health-start-period 10s
steps:
- uses: actions/checkout@v5
- uses: actions/checkout@v6
- name: Set up JDK 21
uses: actions/setup-java@v5
@@ -197,6 +197,9 @@ jobs:
- name: Grant execute permission for gradlew
run: chmod +x gradlew
- name: Static Analysis
run: ./gradlew staticAnalysis --no-daemon
- name: Run integration tests
run: ./gradlew integrationTest --no-daemon --parallel
env:
+10 -210
View File
@@ -1,225 +1,25 @@
name: Docker SSoT Guard
permissions:
contents: read
concurrency:
group: ssot-guard-${{ github.ref }}
cancel-in-progress: true
name: Docker SSoT Guard (Minimal)
on:
push:
branches: [ main ]
paths:
- 'docker/**'
- 'dockerfiles/**'
- 'docker-compose*.yml*'
- 'scripts/**'
- '.github/workflows/ssot-guard.yml'
pull_request:
paths:
- 'docker/**'
- 'dockerfiles/**'
- 'docker-compose*.yml*'
- 'scripts/**'
- '.github/workflows/ssot-guard.yml'
jobs:
ssot-guard:
check-compose-config:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v5
with:
fetch-depth: 0
- uses: actions/checkout@v4
# FIX: .env aus Example erstellen, damit Variablen da sind
- name: Create .env context
run: cp docker/.env.example docker/.env
- name: Show environment
run: |
bash --version
docker --version || true
compose_ver=$(docker compose version 2>/dev/null || true); echo "docker compose: $compose_ver"
- name: Sync versions to env files
run: bash scripts/docker-versions-update.sh sync
- name: Generate docker-compose files (all)
run: bash scripts/generate-compose-files.sh all development
- name: Validate Docker SSoT consistency
run: bash scripts/validate-docker-consistency.sh all
- name: Build vs Runtime variable guards
run: |
set -euo pipefail
echo "[Guard] Prüfe, dass keine Laufzeit-Variablen in Build-Args-Dateien vorkommen..."
RUNTIME_KEYS_REGEX='^(GATEWAY_HOST|GATEWAY_PORT|WEB_APP_PORT|NODE_ENV|CONSUL_(HOST|PORT|ENABLED)|DB_(HOST|PORT|NAME|USER|USERNAME|PASSWORD)|POSTGRES_DB|REDIS_PORT|KEYCLOAK_PORT|PING_SERVICE_PORT|MEMBERS_SERVICE_PORT|HORSES_SERVICE_PORT|EVENTS_SERVICE_PORT|MASTERDATA_SERVICE_PORT|AUTH_SERVICE_PORT|MONITORING_SERVER_PORT|PROMETHEUS_PORT|GRAFANA_PORT|JWT_ISSUER|JWT_AUDIENCE)$'
FAIL=0
shopt -s nullglob
for f in docker/build-args/*.env config/build/*.env; do
[ -f "$f" ] || continue
BAD=$(grep -E '^[A-Z0-9_]+=' "$f" | cut -d= -f1 | grep -E "$RUNTIME_KEYS_REGEX" || true)
if [ -n "$BAD" ]; then
echo "Fehler: Laufzeit-Variablen in Build-Args Datei $f gefunden:"; echo "$BAD"; FAIL=1
fi
done
shopt -u nullglob
if [ $FAIL -ne 0 ]; then
echo "Build vs Runtime Trennung verletzt."; exit 1; fi
echo "[Guard] Prüfe, dass keine Build-/Versions-Variablen in Runtime-Env vorkommen..."
BUILD_KEYS_REGEX='^(GRADLE_VERSION|JAVA_VERSION|VERSION|APP_VERSION|[A-Z]+_IMAGE_TAG)$'
shopt -s nullglob
for f in config/env/.env .env.template; do
[ -f "$f" ] || continue
BAD=$(grep -E '^[A-Z0-9_]+=' "$f" | cut -d= -f1 | grep -E "$BUILD_KEYS_REGEX" || true)
if [ -n "$BAD" ]; then
echo "Fehler: Build-/Versions-Variablen in Runtime-Env $f gefunden:"; echo "$BAD"; FAIL=1
fi
done
shopt -u nullglob
if [ $FAIL -ne 0 ]; then
echo "Build-/Runtime-Mischung in Runtime-Env."; exit 1; fi
- name: Check versions.toml vs global.env consistency
run: |
set -euo pipefail
TOML=docker/versions.toml
GLOBAL=docker/build-args/global.env
[ -f "$TOML" ] || { echo "Missing $TOML"; exit 1; }
[ -f "$GLOBAL" ] || { echo "Missing $GLOBAL"; exit 1; }
get_toml_ver(){ awk -F'=' -v key="$1" '/^\[versions\]/{in_vers=1; next} /^\[/{in_vers=0} in_vers && gsub(/^[ \t]+|[ \t]+$/,"",$1) && $1==key {gsub(/[ "\t]/,"",$2); print $2; exit}' "$TOML"; }
mapfile -t checks < <(printf "%s\n" \
"GRADLE_VERSION:versions.gradle" \
"JAVA_VERSION:versions.java" \
"VERSION:versions.app-version" \
"PROMETHEUS_IMAGE_TAG:versions.prometheus" \
"GRAFANA_IMAGE_TAG:versions.grafana" \
"KEYCLOAK_IMAGE_TAG:versions.keycloak" \
"POSTGRES_IMAGE_TAG:versions.postgres" \
"REDIS_IMAGE_TAG:versions.redis" \
"CONSUL_IMAGE_TAG:versions.consul" \
"ZOOKEEPER_IMAGE_TAG:versions.zookeeper" \
"KAFKA_IMAGE_TAG:versions.kafka")
FAIL=0
for entry in "${checks[@]}"; do
var=${entry%%:*}; path=${entry##*:}
key=${path#*.}
case "$var" in
GRADLE_VERSION) expected=$(get_toml_ver gradle) ;;
JAVA_VERSION) expected=$(get_toml_ver java) ;;
VERSION) expected=$(get_toml_ver app-version) ;;
PROMETHEUS_IMAGE_TAG) expected=$(get_toml_ver prometheus) ;;
GRAFANA_IMAGE_TAG) expected=$(get_toml_ver grafana) ;;
KEYCLOAK_IMAGE_TAG) expected=$(get_toml_ver keycloak) ;;
POSTGRES_IMAGE_TAG) expected=$(get_toml_ver postgres) ;;
REDIS_IMAGE_TAG) expected=$(get_toml_ver redis) ;;
CONSUL_IMAGE_TAG) expected=$(get_toml_ver consul) ;;
ZOOKEEPER_IMAGE_TAG) expected=$(get_toml_ver zookeeper) ;;
KAFKA_IMAGE_TAG) expected=$(get_toml_ver kafka) ;;
esac
actual=$(grep -E "^${var}=" "$GLOBAL" | head -n1 | cut -d= -f2-)
if [ -z "$actual" ] || [ "$actual" != "$expected" ]; then
echo "Versions-Drift: $var global.env='$actual' != versions.toml('$expected')"; FAIL=1
fi
done
if [ $FAIL -ne 0 ]; then
echo "Versions SSoT-Drift erkannt."; exit 1; fi
- name: Check drift of generated artifacts (ignore timestamps)
run: |
set -euo pipefail
# Gather modified files after sync+generate
CHANGED=$(git diff --name-only)
if [ -z "$CHANGED" ]; then
echo "No drift detected."
exit 0
fi
echo "Changed files:" $CHANGED
fail=0
for f in $CHANGED; do
# Inspect actual content changes but ignore volatile timestamp/comment lines
# Ignore lines starting with + or - that are exactly the timestamp markers we generate
DIFF_FILTERED=$(git diff --unified=0 -- "$f" \
| awk 'BEGIN{show=0} { \
if ($0 ~ /^\+\+\+|^---|^@@/) { next } \
if ($0 ~ /^[+-]# (Generated:|Last updated:)/) { next } \
if ($0 ~ /^[+-]#\s*Generated from docker\/versions.toml/) { next } \
if ($0 ~ /^[+-]#\s*Environment:/) { next } \
if ($0 ~ /^[+-]#\s*Source:/) { next } \
if ($0 ~ /^[+-]$/) { next } \
if ($0 ~ /^[+-]/) { print $0 } \
}')
if [ -n "$DIFF_FILTERED" ]; then
echo "SSoT drift detected in $f:";
echo "$DIFF_FILTERED";
fail=1;
fi
done
if [ $fail -ne 0 ]; then
echo "\nERROR: Generated artifacts differ from repository (beyond timestamps)."
echo "Run:"
echo " bash scripts/docker-versions-update.sh sync"
echo " bash scripts/generate-compose-files.sh all"
echo "and commit the changes."
exit 1
fi
echo "No SSoT drift (ignoring timestamps)."
ssot-guard-envless:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v5
with:
fetch-depth: 0
- name: Show environment
run: |
bash --version
docker --version || true
compose_ver=$(docker compose version 2>/dev/null || true); echo "docker compose: $compose_ver"
- name: Generate docker-compose files (all)
run: bash scripts/generate-compose-files.sh all development
- name: Validate Docker SSoT consistency (envless)
run: DOCKER_SSOT_MODE=envless bash scripts/validate-docker-consistency.sh all
- name: Check drift of generated artifacts (ignore timestamps)
run: |
set -euo pipefail
CHANGED=$(git diff --name-only)
if [ -z "$CHANGED" ]; then
echo "No drift detected."
exit 0
fi
echo "Changed files:" $CHANGED
fail=0
for f in $CHANGED; do
DIFF_FILTERED=$(git diff --unified=0 -- "$f" \
| awk 'BEGIN{show=0} { \
if ($0 ~ /^\+\+\+|^---|^@@/) { next } \
if ($0 ~ /^[+-]# (Generated:|Last updated:)/) { next } \
if ($0 ~ /^[+-]#\s*Generated from docker\/versions.toml/) { next } \
if ($0 ~ /^[+-]#\s*Environment:/) { next } \
if ($0 ~ /^[+-]#\s*Source:/) { next } \
if ($0 ~ /^[+-]$/) { next } \
if ($0 ~ /^[+-]/) { print $0 } \
}')
if [ -n "$DIFF_FILTERED" ]; then
echo "SSoT drift detected in $f:";
echo "$DIFF_FILTERED";
fail=1;
fi
done
if [ $fail -ne 0 ]; then
echo "\nERROR: Generated artifacts differ from repository (beyond timestamps)."
echo "Run:"
echo " DOCKER_SSOT_MODE=envless bash scripts/generate-compose-files.sh all"
echo "and commit the changes."
exit 1
fi
echo "No SSoT drift (ignoring timestamps)."
# FIX: .yaml Extension nutzen (SSoT)
- name: Validate Docker Compose Config
run: docker compose --env-file docker/.env -f docker/docker-compose.yaml config
+1 -1
View File
@@ -23,7 +23,7 @@ jobs:
steps:
# WICHTIG: Checkout ist notwendig, damit "git log" funktioniert
- name: Checkout Code
uses: actions/checkout@v4
uses: actions/checkout@v6
with:
fetch-depth: 0 # Notwendig, um die Commit-Historie für "git log" zu laden