forked from red-hat-storage/ocs-client-operator
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request red-hat-storage#115 from leelavg/5496-webhook
implement webhook for validating ocs-client-operator subscription channel
- Loading branch information
Showing
12 changed files
with
308 additions
and
22 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,6 @@ | ||
resources: | ||
- manager.yaml | ||
- webhook_service.yaml | ||
|
||
generatorOptions: | ||
disableNameSuffixHash: true | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
apiVersion: v1 | ||
kind: Service | ||
metadata: | ||
annotations: | ||
service.beta.openshift.io/serving-cert-secret-name: webhook-cert-secret | ||
name: webhook-server | ||
namespace: system | ||
spec: | ||
ports: | ||
- name: https | ||
port: 443 | ||
protocol: TCP | ||
targetPort: 7443 | ||
selector: | ||
app: ocs-client-operator | ||
type: ClusterIP |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -10,6 +10,7 @@ rules: | |
verbs: | ||
- get | ||
- list | ||
- patch | ||
- apiGroups: | ||
- "" | ||
resources: | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -26,11 +26,14 @@ import ( | |
"github.com/red-hat-storage/ocs-client-operator/pkg/console" | ||
"github.com/red-hat-storage/ocs-client-operator/pkg/csi" | ||
"github.com/red-hat-storage/ocs-client-operator/pkg/templates" | ||
"github.com/red-hat-storage/ocs-client-operator/pkg/utils" | ||
|
||
"github.com/go-logr/logr" | ||
configv1 "github.com/openshift/api/config/v1" | ||
secv1 "github.com/openshift/api/security/v1" | ||
opv1a1 "github.com/operator-framework/api/pkg/operators/v1alpha1" | ||
monitoringv1 "github.com/prometheus-operator/prometheus-operator/pkg/apis/monitoring/v1" | ||
admrv1 "k8s.io/api/admissionregistration/v1" | ||
appsv1 "k8s.io/api/apps/v1" | ||
corev1 "k8s.io/api/core/v1" | ||
extv1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" | ||
|
@@ -57,9 +60,10 @@ const ( | |
operatorConfigMapName = "ocs-client-operator-config" | ||
// ClusterVersionName is the name of the ClusterVersion object in the | ||
// openshift cluster. | ||
clusterVersionName = "version" | ||
|
||
deployCSIKey = "DEPLOY_CSI" | ||
clusterVersionName = "version" | ||
deployCSIKey = "DEPLOY_CSI" | ||
subscriptionLabelKey = "managed-by" | ||
subscriptionLabelValue = "webhook.subscription.ocs.openshift.io" | ||
) | ||
|
||
// ClusterVersionReconciler reconciles a ClusterVersion object | ||
|
@@ -106,10 +110,29 @@ func (c *ClusterVersionReconciler) SetupWithManager(mgr ctrl.Manager) error { | |
}, | ||
) | ||
|
||
subscriptionPredicates := builder.WithPredicates( | ||
predicate.NewPredicateFuncs( | ||
func(client client.Object) bool { | ||
return client.GetNamespace() == c.OperatorNamespace | ||
}, | ||
), | ||
predicate.LabelChangedPredicate{}, | ||
) | ||
|
||
webhookPredicates := builder.WithPredicates( | ||
predicate.NewPredicateFuncs( | ||
func(client client.Object) bool { | ||
return client.GetName() == templates.SubscriptionWebhookName | ||
}, | ||
), | ||
) | ||
|
||
return ctrl.NewControllerManagedBy(mgr). | ||
For(&configv1.ClusterVersion{}, clusterVersionPredicates). | ||
Watches(&corev1.ConfigMap{}, enqueueClusterVersionRequest, configMapPredicates). | ||
Watches(&extv1.CustomResourceDefinition{}, enqueueClusterVersionRequest, builder.OnlyMetadata). | ||
Watches(&opv1a1.Subscription{}, enqueueClusterVersionRequest, subscriptionPredicates). | ||
Watches(&admrv1.ValidatingWebhookConfiguration{}, enqueueClusterVersionRequest, webhookPredicates). | ||
Complete(c) | ||
} | ||
|
||
|
@@ -127,6 +150,8 @@ func (c *ClusterVersionReconciler) SetupWithManager(mgr ctrl.Manager) error { | |
//+kubebuilder:rbac:groups=monitoring.coreos.com,resources=prometheusrules,verbs=get;list;watch;create;update | ||
//+kubebuilder:rbac:groups="",resources=services,verbs=get;list;watch;create;update;patch;delete | ||
//+kubebuilder:rbac:groups=console.openshift.io,resources=consoleplugins,verbs=* | ||
//+kubebuilder:rbac:groups=operators.coreos.com,resources=subscriptions,verbs=get;list;watch;update | ||
//+kubebuilder:rbac:groups=admissionregistration.k8s.io,resources=validatingwebhookconfigurations,verbs=get;list;update;create;watch | ||
|
||
// For more details, check Reconcile and its Result here: | ||
// - https://pkg.go.dev/sigs.k8s.io/[email protected]/pkg/reconcile | ||
|
@@ -135,6 +160,16 @@ func (c *ClusterVersionReconciler) Reconcile(ctx context.Context, req ctrl.Reque | |
c.log = log.FromContext(ctx, "ClusterVersion", req) | ||
c.log.Info("Reconciling ClusterVersion") | ||
|
||
if err := c.reconcileSubscriptionValidatingWebhook(); err != nil { | ||
c.log.Error(err, "unable to register subscription validating webhook") | ||
return ctrl.Result{}, err | ||
} | ||
|
||
if err := labelClientOperatorSubscription(c); err != nil { | ||
c.log.Error(err, "unable to label ocs client operator subscription") | ||
return ctrl.Result{}, err | ||
} | ||
|
||
if err := c.ensureConsolePlugin(); err != nil { | ||
c.log.Error(err, "unable to deploy client console") | ||
return ctrl.Result{}, err | ||
|
@@ -494,3 +529,81 @@ func (c *ClusterVersionReconciler) getDeployCSIConfig() (bool, error) { | |
func (c *ClusterVersionReconciler) get(obj client.Object, opts ...client.GetOption) error { | ||
return c.Get(c.ctx, client.ObjectKeyFromObject(obj), obj, opts...) | ||
} | ||
|
||
func (c *ClusterVersionReconciler) reconcileSubscriptionValidatingWebhook() error { | ||
whConfig := &admrv1.ValidatingWebhookConfiguration{} | ||
whConfig.Name = templates.SubscriptionWebhookName | ||
|
||
// TODO (lgangava): after change to configmap controller, need to remove webhook during deletion | ||
err := c.createOrUpdate(whConfig, func() error { | ||
|
||
// openshift fills in the ca on finding this annotation | ||
whConfig.Annotations = map[string]string{ | ||
"service.beta.openshift.io/inject-cabundle": "true", | ||
} | ||
|
||
var caBundle []byte | ||
if len(whConfig.Webhooks) == 0 { | ||
whConfig.Webhooks = make([]admrv1.ValidatingWebhook, 1) | ||
} else { | ||
// do not mutate CA bundle that was injected by openshift | ||
caBundle = whConfig.Webhooks[0].ClientConfig.CABundle | ||
} | ||
|
||
// webhook desired state | ||
var wh *admrv1.ValidatingWebhook = &whConfig.Webhooks[0] | ||
templates.SubscriptionValidatingWebhook.DeepCopyInto(wh) | ||
|
||
wh.Name = whConfig.Name | ||
// only send requests received from own namespace | ||
wh.NamespaceSelector = &metav1.LabelSelector{ | ||
MatchLabels: map[string]string{ | ||
"kubernetes.io/metadata.name": c.OperatorNamespace, | ||
}, | ||
} | ||
// only send resources matching the label | ||
wh.ObjectSelector = &metav1.LabelSelector{ | ||
MatchLabels: map[string]string{ | ||
subscriptionLabelKey: subscriptionLabelValue, | ||
}, | ||
} | ||
// preserve the existing (injected) CA bundle if any | ||
wh.ClientConfig.CABundle = caBundle | ||
// send request to the service running in own namespace | ||
wh.ClientConfig.Service.Namespace = c.OperatorNamespace | ||
|
||
return nil | ||
}) | ||
|
||
if err != nil { | ||
return err | ||
} | ||
|
||
c.log.Info("successfully registered validating webhook") | ||
return nil | ||
} | ||
|
||
func labelClientOperatorSubscription(c *ClusterVersionReconciler) error { | ||
subscriptionList := &opv1a1.SubscriptionList{} | ||
err := c.List(c.ctx, subscriptionList, client.InNamespace(c.OperatorNamespace)) | ||
if err != nil { | ||
return fmt.Errorf("failed to list subscriptions") | ||
} | ||
|
||
sub := utils.Find(subscriptionList.Items, func(sub *opv1a1.Subscription) bool { | ||
return sub.Spec.Package == "ocs-client-operator" | ||
}) | ||
|
||
if sub == nil { | ||
return fmt.Errorf("failed to find subscription with ocs-client-operator package") | ||
} | ||
|
||
if utils.AddLabel(sub, subscriptionLabelKey, subscriptionLabelValue) { | ||
if err := c.Update(c.ctx, sub); err != nil { | ||
return err | ||
} | ||
} | ||
|
||
c.log.Info("successfully labelled ocs-client-operator subscription") | ||
return nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.