From edf5335736571f1c27cdeb8f4cbd42e54a90f903 Mon Sep 17 00:00:00 2001 From: qwerty287 <80460567+qwerty287@users.noreply.github.com> Date: Thu, 20 Aug 2026 13:29:09 +0200 Subject: [PATCH] k8s: allow to disable runtime class name backend option (#7046) Co-authored-by: Robert Kaussow --- cmd/cli/app_test.go | 3 ++- .../10-configuration/11-backends/20-kubernetes.md | 9 +++++++++ pipeline/backend/kubernetes/flags.go | 6 ++++++ pipeline/backend/kubernetes/kubernetes.go | 2 ++ pipeline/backend/kubernetes/pod.go | 5 ++++- pipeline/backend/kubernetes/pod_test.go | 1 + 6 files changed, 24 insertions(+), 2 deletions(-) diff --git a/cmd/cli/app_test.go b/cmd/cli/app_test.go index b04ce3536..35c3c06e5 100644 --- a/cmd/cli/app_test.go +++ b/cmd/cli/app_test.go @@ -45,7 +45,8 @@ func TestNewAppRunsDecodeBase64WithoutConfig(t *testing.T) { } command := exec.CommandContext(t.Context(), os.Args[0], "-test.run=^TestNewAppRunsDecodeBase64WithoutConfig$") - command.Env = append(os.Environ(), + command.Env = append( + os.Environ(), "WOODPECKER_DECODE_BASE64_HELPER=1", "WOODPECKER_DISABLE_UPDATE_CHECK=true", "XDG_CONFIG_HOME="+t.TempDir(), diff --git a/docs/docs/30-administration/10-configuration/11-backends/20-kubernetes.md b/docs/docs/30-administration/10-configuration/11-backends/20-kubernetes.md index 788bb1cd4..1122aa6a5 100644 --- a/docs/docs/30-administration/10-configuration/11-backends/20-kubernetes.md +++ b/docs/docs/30-administration/10-configuration/11-backends/20-kubernetes.md @@ -673,3 +673,12 @@ Container image used for the workspace permission init container, which is used - Default: `false` Determines if the Pod `serviceAccountName` can be defined from a step's backend options. Disabled by default, as it would otherwise allow any user with push access to run pods under an arbitrary service account and escalate privileges. + +--- + +### BACKEND_K8S_RUNTIME_CLASS_ALLOW_FROM_STEP + +- Name: `WOODPECKER_BACKEND_K8S_RUNTIME_CLASS_ALLOW_FROM_STEP` +- Default: `false` + +Determines if the Pod `runtimeClassName` can be defined from a step's backend options. Disabled by default, as it would otherwise allow any user with push access to run pods under an arbitrary runtime class. diff --git a/pipeline/backend/kubernetes/flags.go b/pipeline/backend/kubernetes/flags.go index ff1b92a86..ff2b7ea8d 100644 --- a/pipeline/backend/kubernetes/flags.go +++ b/pipeline/backend/kubernetes/flags.go @@ -115,6 +115,12 @@ var Flags = []cli.Flag{ Usage: "whether to allow using affinity from step's backend options", Value: false, }, + &cli.BoolFlag{ + Sources: cli.EnvVars("WOODPECKER_BACKEND_K8S_RUNTIME_CLASS_ALLOW_FROM_STEP"), + Name: "backend-k8s-runtime-class-allow-from-step", + Usage: "whether to allow using runtime class name from step's backend options", + Value: false, + }, &cli.BoolFlag{ Sources: cli.EnvVars("WOODPECKER_BACKEND_K8S_SECCTX_NONROOT"), // cspell:words secctx nonroot Name: "backend-k8s-secctx-nonroot", diff --git a/pipeline/backend/kubernetes/kubernetes.go b/pipeline/backend/kubernetes/kubernetes.go index 67aec4469..a8aad184a 100644 --- a/pipeline/backend/kubernetes/kubernetes.go +++ b/pipeline/backend/kubernetes/kubernetes.go @@ -75,6 +75,7 @@ type config struct { PodTolerations []Toleration PodAffinity *kube_core_v1.Affinity PodAffinityAllowFromStep bool + RuntimeClassAllowFromStep bool ImagePullSecretNames []string SecurityContext SecurityContextConfig NativeSecretsAllowFromStep bool @@ -124,6 +125,7 @@ func configFromCliContext(ctx context.Context) (*config, error) { PodNodeSelectorAllowFromStep: c.Bool("backend-k8s-pod-node-selector-allow-from-step"), PodNodeSelector: make(map[string]string), // just init empty map to prevent nil panic PodAffinityAllowFromStep: c.Bool("backend-k8s-pod-affinity-allow-from-step"), + RuntimeClassAllowFromStep: c.Bool("backend-k8s-runtime-class-allow-from-step"), ImagePullSecretNames: c.StringSlice("backend-k8s-pod-image-pull-secret-names"), SecurityContext: SecurityContextConfig{ RunAsNonRoot: c.Bool("backend-k8s-secctx-nonroot"), // cspell:words secctx nonroot diff --git a/pipeline/backend/kubernetes/pod.go b/pipeline/backend/kubernetes/pod.go index b62b2743b..8e33d7fc2 100644 --- a/pipeline/backend/kubernetes/pod.go +++ b/pipeline/backend/kubernetes/pod.go @@ -184,7 +184,6 @@ func podSpec(step *types.Step, config *config, options BackendOptions, nsp nativ spec := kube_core_v1.PodSpec{ RestartPolicy: kube_core_v1.RestartPolicyNever, - RuntimeClassName: options.RuntimeClassName, PriorityClassName: config.PriorityClassName, HostAliases: hostAliases(step.ExtraHosts), Hostname: getHostnameOrEmpty(step.Name), @@ -202,6 +201,10 @@ func podSpec(step *types.Step, config *config, options BackendOptions, nsp nativ spec.ServiceAccountName = options.ServiceAccountName } + if config.RuntimeClassAllowFromStep { + spec.RuntimeClassName = options.RuntimeClassName + } + // If there are tolerations and they are allowed if config.PodTolerationsAllowFromStep && len(options.Tolerations) != 0 { spec.Tolerations = tolerations(options.Tolerations) diff --git a/pipeline/backend/kubernetes/pod_test.go b/pipeline/backend/kubernetes/pod_test.go index 308bedac3..753e7b199 100644 --- a/pipeline/backend/kubernetes/pod_test.go +++ b/pipeline/backend/kubernetes/pod_test.go @@ -557,6 +557,7 @@ func TestFullPod(t *testing.T) { PodNodeSelectorAllowFromStep: true, SecurityContext: SecurityContextConfig{RunAsNonRoot: false}, ServiceAccountNameAllowFromStep: true, + RuntimeClassAllowFromStep: true, }, "wp-01he8bebctabr3kgk0qj36d2me-0", "linux/amd64",