Files
hsiegeln 242ef1f0af
All checks were successful
CI / cleanup-branch (push) Has been skipped
CI / build (push) Successful in 1m43s
CI / docker (push) Successful in 4m13s
CI / deploy-feature (push) Has been skipped
CI / deploy (push) Successful in 41s
perf(build): faster Maven + UI + CI pipelines
- Maven: enable useIncrementalCompilation; Surefire forkCount=1C +
  reuseForks=true so unit-test JVMs are reused per CPU core instead of
  spawning per class (205 tests pass under the new strategy).
- Testcontainers: opt-in reuse via .withReuse(true) on Postgres +
  ClickHouse base; per-developer enable via ~/.testcontainers.properties.
- UI: drop redundant `tsc --noEmit` from `npm run build` (Vite already
  type-checks); split into a dedicated `npm run typecheck` script.
- CI: cache ~/.npm and ui/node_modules/.vite alongside Maven; npm ci with
  --prefer-offline --no-audit --fund=false; paths-ignore for docs-only,
  .planning/ and .claude/ changes so doc-only pushes skip the pipeline.
- Docs: CLAUDE.md + .claude/rules/cicd.md updated with the new build
  knobs and the Testcontainers reuse opt-in.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 10:48:34 +02:00

2.8 KiB

paths
paths
.gitea/**
deploy/**
Dockerfile
docker-entrypoint.sh

CI/CD & Deployment

  • CI workflow: .gitea/workflows/ci.yml — build -> docker -> deploy on push to main or feature branches. paths-ignore skips the whole pipeline for docs-only / .planning/ / .claude/ / *.md changes (push and PR triggers).
  • Build step skips integration tests (-DskipITs) — Testcontainers needs Docker daemon
  • Build caches (parallel actions/cache@v4 steps in the build job): ~/.m2/repository (key on all pom.xml), ~/.npm (key on ui/package-lock.json), ui/node_modules/.vite (key on ui/package-lock.json + ui/vite.config.ts). UI install uses npm ci --prefer-offline --no-audit --fund=false so the npm cache is the primary source.
  • Maven build performance (set in pom.xml and cameleer-server-app/pom.xml): useIncrementalCompilation=true on the compiler plugin; Surefire uses forkCount=1C + reuseForks=true (one JVM per CPU core, reused across test classes); Failsafe keeps forkCount=1 + reuseForks=true. Unit tests must not rely on per-class JVM isolation.
  • UI build script (ui/package.json): build is vite build only — the type-check pass was split out into npm run typecheck (run separately when you want a full tsc --noEmit sweep).
  • Docker: multi-stage build (Dockerfile), $BUILDPLATFORM for native Maven on ARM64 runner, amd64 runtime. docker-entrypoint.sh imports /certs/ca.pem into JVM truststore before starting the app (supports custom CAs for OIDC discovery without CAMELEER_SERVER_SECURITY_OIDCTLSSKIPVERIFY).
  • REGISTRY_TOKEN build arg required for cameleer-common dependency resolution
  • Registry: gitea.siegeln.net/cameleer/cameleer-server (container images)
  • K8s manifests in deploy/ — Kustomize base + overlays (main/feature), shared infra (PostgreSQL, ClickHouse, Logto) as top-level manifests
  • Deployment target: k3s at 192.168.50.86, namespace cameleer (main), cam-<slug> (feature branches)
  • Feature branches: isolated namespace, PG schema; Traefik Ingress at <slug>-api.cameleer.siegeln.net
  • Secrets managed in CI deploy step (idempotent --dry-run=client | kubectl apply): cameleer-auth, cameleer-postgres-credentials, cameleer-clickhouse-credentials
  • K8s probes: server uses /api/v1/health, PostgreSQL uses pg_isready -U "$POSTGRES_USER" (env var, not hardcoded)
  • K8s security: server and database pods run with securityContext.runAsNonRoot. UI (nginx) runs without securityContext (needs root for entrypoint setup).
  • Docker: server Dockerfile has no default credentials — all DB config comes from env vars at runtime
  • Docker build uses buildx registry cache + --provenance=false for Gitea compatibility
  • CI: branch slug sanitization extracted to .gitea/sanitize-branch.sh, sourced by docker and deploy-feature jobs