Ga naar inhoud

Onboarding / registration steps

The manifests these steps reference (runner Deployment, ArgoCD AppProject/Application) exist under manifests/ and are live on con-prod. All kubectl/argocd examples use an explicit --kubeconfig <path> (no aliases) for the audit trail.

1. Codeberg — enroll the forgejo-runner (connection model, no register)

Verified on con-prod (runner v12.12.0). forgejo-runner register is deprecated on Codeberg and fails ("registration token not found", forgejo/forgejo#4890); the offline create-runner-file --secret needs server-admin we don't have. The working path is the v12 connection model: Codeberg's Create new runner gives a uuid + token that you declare directly in the daemon config (server.connections). No register, no .runner.

Model: ONE org-scope runner. A single organization-scope connection serves every Conduction repo that has Actions enabled — one token, no per-repo enrollment. The repo allowlist is simply "which repos have Actions on". The connection token is long-lived (only dies if the runner is deleted/rotated), so no routine re-enrollment.

One-time enrollment (org admin):

  1. Codeberg → organization Conduction → Settings → Actions → Runners → Create new runner (org admin rights required). Copy the UUID and token from that screen (they are a pair — use both from the same screen).
  2. Put them into the runner config (server.connections, one entry) and store it as the SOPS-encrypted Secret forgejo-runner-conn (key config.yml) — see manifests/components/runner-secrets/. The config holds the token, so it is a Secret, never a ConfigMap, committed only SOPS+age-encrypted. It is not a Codeberg Actions secret.
  3. The daemon runs forgejo-runner daemon --config /config/config.yml; it declares the connection and polls. runner.capacity sets simultaneous jobs (host backend → jobs share the runner pod; size pod + quota accordingly).

Adding a repo (the allowlist): just enable Actions on the repo — repo Settings → Units/Overview → tick Actions, then add .forgejo/workflows/*.yaml with a Talos label. No new runner, no token, no config change. A repo without Actions enabled cannot use the runner (default-deny by repo).

Which label? (con-ci vs con-ci-oci)

Talos serves only its own labels — generic docker/ubuntu-latest are NOT served, so a job on those just sits queued forever. Pick:

Job Label
lint / Semgrep / Trivy (host tools), kubectl/ops, the Nextcloud sign step con-ci (host)
any job with a container: image or services:; Hydra personas; building OCI images (podman build) con-ci-oci (container)

Heuristic (revised 2026-07-04): plain host job → con-ci; anything involving container images — running AND building — → con-ci-oci.

Guardrail so devs don't sit queued

scripts/check-forgejo-runs-on.sh validates workflow labels (run it, or wire it as a pre-commit hook). It fails on unsupported labels and on container:/services: jobs that aren't con-ci-oci. In a consuming repo's .pre-commit-config.yaml:

- repo: https://codeberg.org/Conduction/talos
  rev: <tag-or-sha>
  hooks:
    - id: forgejo-runs-on

(Requires yq on the dev machine. Run manually: scripts/check-forgejo-runs-on.sh path/to/wf.yml.)

Quick manual bring-up (no SOPS, e.g. a smoke runner): create the Secret straight from a local config — kubectl --kubeconfig <path> -n con-ci create secret generic forgejo-runner-conn --from-file=config.yml=./config.yml — and apply the runner Deployment.

Rotation. Delete the runner in the Codeberg UI, Create new runner (org) again, update the Secret, re-sync. (Per-repo cryptographic isolation or an auto-enrollment operator — declarative repo list + registration-token API + self-heal — is deferred to Change-2.)

2. ArgoCD — bootstrap the Application (one-time, then GitOps takes over)

House style (observed in cluster-infra/argo/): AppProject under argo/projects/, Application under argo/applications/, multiSource (chart/overlay + $values from the Codeberg repo), app.kubernetes.io/part-of label, a finalizer, and syncPolicy.automated with prune + selfHeal.

Steps (operator, once):

  1. Register this repo as an ArgoCD source if not already trusted. Conduction's other Codeberg repos (e.g. cluster-infra) are already registered, so prefer reusing the existing repo-creds Secret/pattern over adding a new credential:

argocd repo add https://codeberg.org/Conduction/talos.git --username --password

  1. Apply the AppProject (RBAC guardrails scoped to the CI namespace):

kubectl --kubeconfig apply -f argo/projects/.yaml

  1. Apply the Application:

kubectl --kubeconfig apply -f argo/applications/talos.yaml

  1. ArgoCD reconciles automatically (selfHeal + prune). Verify:

argocd app get talos

Rollback. Delete the Applicationprune removes the managed resources and the CI namespace drains (see the gitops-delivery spec).

Prerequisites still open (carried from design.md)

  • Confirm con-prod's CNI before the apply phase (vanilla NetworkPolicy assumed; no Cilium toFQDNs confirmed). The egress-proxy approach was chosen precisely so enrollment does not depend on CNI FQDN support.