Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions manifests/01-config-managed-role-binding.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: cloud-credential-operator
namespace: openshift-config-managed
annotations:
capability.openshift.io/name: CloudCredential
include.release.openshift.io/ibm-cloud-managed: "true"
include.release.openshift.io/self-managed-high-availability: "true"
subjects:
- kind: ServiceAccount
name: cloud-credential-operator
namespace: openshift-cloud-credential-operator
roleRef:
kind: Role
apiGroup: rbac.authorization.k8s.io
name: cloud-credential-operator-role
18 changes: 18 additions & 0 deletions manifests/01-config-managed-role.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: cloud-credential-operator-role
namespace: openshift-config-managed
annotations:
capability.openshift.io/name: CloudCredential
include.release.openshift.io/ibm-cloud-managed: "true"
include.release.openshift.io/self-managed-high-availability: "true"
rules:
- apiGroups:
- ""
resources:
- configmaps
resourceNames:
- kube-cloud-config
verbs:
- "get"
2 changes: 1 addition & 1 deletion manifests/01-config-role-binding.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: cloud-credential-operator
namespace: openshift-config-managed
namespace: openshift-config
annotations:
capability.openshift.io/name: CloudCredential
include.release.openshift.io/ibm-cloud-managed: "true"
Expand Down
8 changes: 5 additions & 3 deletions manifests/01-config-role.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: cloud-credential-operator-role
namespace: openshift-config-managed
namespace: openshift-config
annotations:
capability.openshift.io/name: CloudCredential
include.release.openshift.io/ibm-cloud-managed: "true"
Expand All @@ -13,6 +13,8 @@ rules:
resources:
- configmaps
resourceNames:
- kube-cloud-config
- cloud-provider-config
verbs:
- "get"
- get
- list
- watch
28 changes: 25 additions & 3 deletions pkg/operator/secretannotator/openstack/reconciler.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ package openstack

import (
"context"
"errors"
"fmt"
"time"

Expand Down Expand Up @@ -52,6 +53,7 @@ func NewReconciler(c client.Client, mgr manager.Manager) reconcile.Reconciler {
r := &ReconcileCloudCredSecret{
Client: c,
RootCredClient: mgr.GetClient(),
LiveClient: utils.LiveClient(mgr),
Logger: log.WithField("controller", constants.SecretAnnotatorControllerName),
}

Expand Down Expand Up @@ -105,6 +107,7 @@ var _ reconcile.Reconciler = &ReconcileCloudCredSecret{}
type ReconcileCloudCredSecret struct {
Client client.Client
RootCredClient client.Client
LiveClient client.Client
Logger log.FieldLogger
}

Expand Down Expand Up @@ -134,7 +137,7 @@ func (r *ReconcileCloudCredSecret) Reconcile(ctx context.Context, request reconc
}
if conflict {
r.Logger.Error("configuration conflict between legacy configmap and operator config")
return reconcile.Result{}, fmt.Errorf("configuration conflict")
return reconcile.Result{}, errors.New("configuration conflict")
}
if mode == operatorv1.CloudCredentialsModeManual {
r.Logger.Info("operator in disabled / manual mode")
Expand All @@ -146,9 +149,11 @@ func (r *ReconcileCloudCredSecret) Reconcile(ctx context.Context, request reconc
default:
const msg = "OpenStack only supports Passthrough mode"
r.Logger.Error(msg)
return reconcile.Result{}, fmt.Errorf(msg)
return reconcile.Result{}, errors.New(msg)
}

r.Logger.Info("verifying clouds.yaml and syncing cacert (if any)")

secret := &corev1.Secret{}
err = r.RootCredClient.Get(context.Background(), request.NamespacedName, secret)
if err != nil {
Expand All @@ -162,13 +167,30 @@ func (r *ReconcileCloudCredSecret) Reconcile(ctx context.Context, request reconc
return reconcile.Result{}, err
}

// Sync the cacert from its legacy location (the 'ca-bundle.pem' key of the
// 'openshift-config / cloud-provider-config' CM) to the new place, if present.
// TODO(stephenfin): Remove this syncer in a future release once CCM no longer
// relies on the legacy place during bootstrapping.
config := &corev1.ConfigMap{}
err = r.LiveClient.Get(context.Background(), types.NamespacedName{Namespace: "openshift-config", Name: "cloud-provider-config"}, config)
if err != nil {
r.Logger.Debugf("cloud provider config not found: %v", err)
return reconcile.Result{}, err
}

cacertUpdated := false
if ccmCACert := config.Data["ca-bundle.pem"]; ccmCACert != cacert {
cacert = ccmCACert
cacertUpdated = true
}

clouds, cloudsUpdated, err := r.fixInvalidCACertFile(clouds)
if err != nil {
r.Logger.WithError(err).Error("errored checking clouds.yaml")
return reconcile.Result{}, err
}

if cloudsUpdated {
if cloudsUpdated || cacertUpdated {
openstack.SetRootCloudCredentialsSecretData(secret, clouds, cacert)
err := r.RootCredClient.Update(context.TODO(), secret)
if err != nil {
Expand Down
16 changes: 14 additions & 2 deletions pkg/operator/secretannotator/openstack/reconciler_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,14 @@ func TestReconcileCloudCredSecret_Reconcile(t *testing.T) {
},
}

ccmConfig := &corev1.ConfigMap{
ObjectMeta: metav1.ObjectMeta{
Name: "cloud-provider-config",
Namespace: "openshift-config",
},
Data: map[string]string{},
}

/*
Test parsing of CCO configuration and the resulting annotation of the
root secret. Most of this is boilerplate behaviour.
Expand Down Expand Up @@ -181,11 +189,13 @@ func TestReconcileCloudCredSecret_Reconcile(t *testing.T) {
secret := testSecret(fmt.Sprintf(cloudsWithCACert, correctCACertFile))
existing := append(tc.existing, infra, testOperatorConfig(tc.mode))
fakeClient := fake.NewClientBuilder().WithRuntimeObjects(existing...).Build()
fakeRootCredClient := fake.NewClientBuilder().WithRuntimeObjects(secret).Build()
fakeRootCredClient := fake.NewClientBuilder().WithRuntimeObjects(secret, ccmConfig).Build()
fakeLiveClient := fake.NewClientBuilder().WithRuntimeObjects(ccmConfig).Build()

r := &ReconcileCloudCredSecret{
Client: fakeClient,
RootCredClient: fakeRootCredClient,
LiveClient: fakeLiveClient,
Logger: log.WithField("controller", "testController"),
}
_, err := r.Reconcile(context.TODO(), reconcile.Request{NamespacedName: types.NamespacedName{
Expand Down Expand Up @@ -270,12 +280,14 @@ func TestReconcileCloudCredSecret_Reconcile(t *testing.T) {
t.Run(tc.name, func(t *testing.T) {
secret := testSecret(tc.cloudsYAML)
fakeClient := fake.NewClientBuilder().WithRuntimeObjects(infra, passthrough).Build()
fakeRootCredClient := fake.NewClientBuilder().WithRuntimeObjects(secret).Build()
fakeRootCredClient := fake.NewClientBuilder().WithRuntimeObjects(secret, ccmConfig).Build()
fakeLiveClient := fake.NewClientBuilder().WithRuntimeObjects(ccmConfig).Build()

t.Logf("clouds.yaml: %s", tc.cloudsYAML)
r := &ReconcileCloudCredSecret{
Client: fakeClient,
RootCredClient: fakeRootCredClient,
LiveClient: fakeLiveClient,
Logger: log.WithField("controller", "testController"),
}

Expand Down