Skip to content

Commit

Permalink
Remove SeccompProfile RuntimeDefault from securityContext on old Open…
Browse files Browse the repository at this point in the history
…Shift clusters

Signed-off-by: Joel Smith <joelsmith@redhat.com>
  • Loading branch information
joelsmith committed Jun 1, 2023
1 parent 388da61 commit 0f6c11f
Show file tree
Hide file tree
Showing 3 changed files with 84 additions and 0 deletions.
18 changes: 18 additions & 0 deletions controllers/keda/kedacontroller_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ import (
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/types"
auditv1 "k8s.io/apiserver/pkg/apis/audit/v1"
"k8s.io/client-go/discovery"
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/client"
"sigs.k8s.io/controller-runtime/pkg/controller/controllerutil"
Expand Down Expand Up @@ -81,6 +82,7 @@ type KedaControllerReconciler struct {
resourcesMetrics mf.Manifest
resourcesWebhooks mf.Manifest
resourcesMonitoring mf.Manifest
discoveryClient *discovery.DiscoveryClient
}

func (r *KedaControllerReconciler) SetupWithManager(mgr ctrl.Manager) error {
Expand All @@ -98,6 +100,7 @@ func (r *KedaControllerReconciler) SetupWithManager(mgr ctrl.Manager) error {
r.resourcesMetrics = manifestMetrics
r.resourcesWebhooks = manifestWebhooks
r.resourcesMonitoring = manifestMonitoring
r.discoveryClient = discovery.NewDiscoveryClientForConfigOrDie(ctrl.GetConfigOrDie())

return ctrl.NewControllerManagedBy(mgr).
For(&kedav1alpha1.KedaController{}).
Expand Down Expand Up @@ -358,6 +361,11 @@ func (r *KedaControllerReconciler) installController(ctx context.Context, logger
transforms = append(transforms, transform.ReplaceKedaOperatorImage(controllerImage, r.Scheme))
}

// on OpenShift 4.10 (kube 1.23) and earlier, the RuntimeDefault SeccompProfile won't validate against any SCC
if util.RunningOnOpenshift(ctx, logger, r.Client) && util.RunningOnClusterWithoutSeccompProfileDefault(logger, r.discoveryClient) {
transforms = append(transforms, transform.RemoveSeccompProfileFromKedaOperator(r.Scheme, logger))
}

if len(instance.Spec.Operator.LogLevel) > 0 {
transforms = append(transforms, transform.ReplaceKedaOperatorLogLevel(instance.Spec.Operator.LogLevel, r.Scheme, logger))
}
Expand Down Expand Up @@ -459,6 +467,11 @@ func (r *KedaControllerReconciler) installMetricsServer(ctx context.Context, log
transforms = append(transforms, transform.ReplaceMetricsServerImage(controllerImage, r.Scheme))
}

// on OpenShift 4.10 (kube 1.23) and earlier, the RuntimeDefault SeccompProfile won't validate against any SCC
if util.RunningOnOpenshift(ctx, logger, r.Client) && util.RunningOnClusterWithoutSeccompProfileDefault(logger, r.discoveryClient) {
transforms = append(transforms, transform.RemoveSeccompProfileFromMetricsServer(r.Scheme, logger))
}

// certificates rotation works only on Openshift due to openshift/service-ca-operator
if util.RunningOnOpenshift(ctx, logger, r.Client) {
if err := r.ensureOpenshiftCABundleConfigMap(ctx, logger, instance); err != nil {
Expand Down Expand Up @@ -725,6 +738,11 @@ func (r *KedaControllerReconciler) installAdmissionWebhooks(ctx context.Context,
transform.ReplaceWatchNamespace(instance.Spec.WatchNamespace, "keda-admission-webhooks", r.Scheme, logger),
}

// on OpenShift 4.10 (kube 1.23) and earlier, the RuntimeDefault SeccompProfile won't validate against any SCC
if util.RunningOnOpenshift(ctx, logger, r.Client) && util.RunningOnClusterWithoutSeccompProfileDefault(logger, r.discoveryClient) {
transforms = append(transforms, transform.RemoveSeccompProfileFromAdmissionWebhooks(r.Scheme, logger))
}

// certificates rotation works only on Openshift due to openshift/service-ca-operator
if util.RunningOnOpenshift(ctx, logger, r.Client) {
serviceName := "keda-admission-webhooks"
Expand Down
40 changes: 40 additions & 0 deletions controllers/keda/transform/transform.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,46 @@ func ReplaceWatchNamespace(watchNamespace string, containerName string, scheme *
}
}

func RemoveSeccompProfile(containerName string, scheme *runtime.Scheme, logger logr.Logger) mf.Transformer {
return func(u *unstructured.Unstructured) error {
changed := false
if u.GetKind() == "Deployment" {
deploy := &appsv1.Deployment{}
if err := scheme.Convert(u, deploy, nil); err != nil {
return err
}
containers := deploy.Spec.Template.Spec.Containers
for i, container := range containers {
if container.Name == containerName {
if container.SecurityContext != nil && container.SecurityContext.SeccompProfile != nil && container.SecurityContext.SeccompProfile.Type == corev1.SeccompProfileTypeRuntimeDefault {
containers[i].SecurityContext.SeccompProfile = nil
changed = true
break
}
}
}
if changed {
if err := scheme.Convert(deploy, u, nil); err != nil {
return err
}
}
}
return nil
}
}

func RemoveSeccompProfileFromKedaOperator(scheme *runtime.Scheme, logger logr.Logger) mf.Transformer {
return RemoveSeccompProfile(containerNameKedaOperator, scheme, logger)
}

func RemoveSeccompProfileFromMetricsServer(scheme *runtime.Scheme, logger logr.Logger) mf.Transformer {
return RemoveSeccompProfile(containerNameMetricsServer, scheme, logger)
}

func RemoveSeccompProfileFromAdmissionWebhooks(scheme *runtime.Scheme, logger logr.Logger) mf.Transformer {
return RemoveSeccompProfile(containerNameAdmissionWebhooks, scheme, logger)
}

func EnsureCABundleInjectionForValidatingWebhookConfiguration(annotation string, annotationValue string, scheme *runtime.Scheme) mf.Transformer {
return func(u *unstructured.Unstructured) error {
if u.GetKind() == "ValidatingWebhookConfiguration" {
Expand Down
26 changes: 26 additions & 0 deletions controllers/keda/util/util.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,14 @@ import (
"context"
"crypto/md5"
"fmt"
"strconv"

"github.com/go-logr/logr"
corev1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/meta"
"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/client-go/discovery"
"sigs.k8s.io/controller-runtime/pkg/client"

kedav1alpha1 "github.com/kedacore/keda-olm-operator/apis/keda/v1alpha1"
Expand Down Expand Up @@ -73,6 +75,30 @@ func RunningOnOpenshift(ctx context.Context, logger logr.Logger, cl client.Clien
return isGvkPresent(ctx, logger, cl, gvk)
}

// RunningOnClusterWithoutSeccompProfileDefault returns true if running on cluster <= 1.23.Z which lacks the RuntimeDefault seccomp profile
func RunningOnClusterWithoutSeccompProfileDefault(logger logr.Logger, discoveryClient *discovery.DiscoveryClient) bool {
var major, minor int

if discoveryClient == nil {
logger.Error(nil, "Unable to get cluster version without discoveryClient")
return false
}
versionInfo, err := discoveryClient.ServerVersion()
if err != nil {
logger.Error(err, "Unable to get cluster version from ServerVersion()")
return false
}
if major, err = strconv.Atoi(versionInfo.Major); err != nil {
logger.Error(err, "Unable to get numeric major cluster version", "major", versionInfo.Major)
return false
}
if minor, err = strconv.Atoi(versionInfo.Minor); err != nil {
logger.Error(err, "Unable to get numeric minor cluster version", "minor", versionInfo.Minor)
return false
}
return major <= 1 && minor <= 23
}

// HasServiceMonitorCRD returns true if the ServiceMonitor CRD is present in the cluster, false otherwise
func HasServiceMonitorCRD(ctx context.Context, logger logr.Logger, cl client.Client) bool {
gvk := schema.GroupVersionKind{Group: "monitoring.coreos.com", Version: "v1", Kind: "ServiceMonitor"}
Expand Down

0 comments on commit 0f6c11f

Please sign in to comment.