From 1b91fb48b740724831c952c583546bd8e984b99e Mon Sep 17 00:00:00 2001 From: Arash Javanmardi Date: Fri, 18 Sep 2026 10:41:33 +0200 Subject: [PATCH] Fix Helm effective namespace validation Signed-off-by: Arash Javanmardi --- .../templates/validation.yml | 11 +-- tests/helm/helm_template_test.go | 74 +++++++++++++++++++ 2 files changed, 75 insertions(+), 10 deletions(-) diff --git a/deployments/helm/nvidia-device-plugin/templates/validation.yml b/deployments/helm/nvidia-device-plugin/templates/validation.yml index 20761ae8c..f44ab155f 100644 --- a/deployments/helm/nvidia-device-plugin/templates/validation.yml +++ b/deployments/helm/nvidia-device-plugin/templates/validation.yml @@ -10,7 +10,7 @@ {{- fail $error }} {{- end }} -{{- if and (eq (include "nvidia-device-plugin.namespace" .) "default") ( eq .Values.namespaceOverride "") (not .Values.allowDefaultNamespace) }} +{{- if and (eq (include "nvidia-device-plugin.namespace" .) "default") (not .Values.allowDefaultNamespace) }} {{- $error := "" }} {{- $error = printf "%s\nRunning in the 'default' namespace is not recommended." $error }} {{- $error = printf "%s\nSet 'allowDefaultNamespace=true' to bypass this error." $error }} @@ -37,12 +37,3 @@ {{- $error = printf "%s\nFallbacks are attempted in order and the current set is %s." $error .Values.config.fallbackStrategies }} {{- fail $error }} {{- end }} - -{{- if and (eq .Release.Namespace "default") (not .Values.allowDefaultNamespace) }} -{{- $error := "" }} -{{- $error = printf "%s\nRunning in the 'default' namespace is not recommended." $error }} -{{- $error = printf "%s\nSet 'allowDefaultNamespace=true' to bypass this error." $error }} -{{- $error = printf "%s\nOtherwise, use --namespace (with --create-namespace as necessary) to run in a specific namespace." $error }} -{{- $error = printf "%s\nSee: https://helm.sh/docs/helm/helm_install/#options" $error }} -{{- fail $error }} -{{- end }} \ No newline at end of file diff --git a/tests/helm/helm_template_test.go b/tests/helm/helm_template_test.go index b0a0044c3..037cd13f8 100644 --- a/tests/helm/helm_template_test.go +++ b/tests/helm/helm_template_test.go @@ -126,6 +126,80 @@ func TestDevicePluginDaemonsetTemplateRenderedDeployment(t *testing.T) { } } +func TestDevicePluginNamespaceValidation(t *testing.T) { + helmChartPath, err := filepath.Abs("../../deployments/helm/nvidia-device-plugin") + require.NoError(t, err) + + testCases := []struct { + description string + releaseNamespace string + namespaceOverride string + expectedNamespace string + }{ + { + description: "default release without override", + releaseNamespace: "default", + expectedNamespace: "default", + }, + { + description: "non-default release without override", + releaseNamespace: "gpu-system", + expectedNamespace: "gpu-system", + }, + { + description: "override default release with non-default namespace", + releaseNamespace: "default", + namespaceOverride: "gpu-system", + expectedNamespace: "gpu-system", + }, + { + description: "override non-default release with default namespace", + releaseNamespace: "gpu-system", + namespaceOverride: "default", + expectedNamespace: "default", + }, + { + description: "override default release with default namespace", + releaseNamespace: "default", + namespaceOverride: "default", + expectedNamespace: "default", + }, + { + description: "override non-default release with another namespace", + releaseNamespace: "gpu-system", + namespaceOverride: "device-plugin", + expectedNamespace: "device-plugin", + }, + } + + for _, tc := range testCases { + for _, allowDefaultNamespace := range []bool{false, true} { + t.Run(fmt.Sprintf("%s/allowDefaultNamespace=%t", tc.description, allowDefaultNamespace), func(t *testing.T) { + options := &helm.Options{ + SetValues: map[string]string{ + "namespaceOverride": tc.namespaceOverride, + "allowDefaultNamespace": fmt.Sprint(allowDefaultNamespace), + }, + KubectlOptions: k8s.NewKubectlOptions("", "", tc.releaseNamespace), + Logger: logger.Discard, + } + + output, err := helm.RenderTemplateE(t, options, helmChartPath, "nvidia-device-plugin", []string{"templates/daemonset-device-plugin.yml"}) + if tc.expectedNamespace == "default" && !allowDefaultNamespace { + require.ErrorContains(t, err, "Running in the 'default' namespace is not recommended.") + require.ErrorContains(t, err, "Set 'allowDefaultNamespace=true' to bypass this error.") + return + } + require.NoError(t, err) + + var daemonSet appsv1.DaemonSet + helm.UnmarshalK8SYaml(t, output, &daemonSet) + require.Equal(t, tc.expectedNamespace, daemonSet.Namespace) + }) + } + } +} + // prt returns a reference to whatever type is passed into it func ptr[T any](x T) *T { return &x