Skip to content

Commit

Permalink
fix cache error
Browse files Browse the repository at this point in the history
  • Loading branch information
m00g3n committed Nov 13, 2023
1 parent 59b1cb1 commit 93651ec
Show file tree
Hide file tree
Showing 2 changed files with 69 additions and 26 deletions.
1 change: 1 addition & 0 deletions api/v1/gardenercluster_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,7 @@ const (
ConditionReasonKubeconfigSecretRotated ConditionReason = "KubeconfigSecretRotated"
ConditionReasonFailedToGetSecret ConditionReason = "FailedToCheckSecret"
ConditionReasonFailedToCreateSecret ConditionReason = "ConditionReasonFailedToCreateSecret"
ConditionReasonFailedToDeleteSecret ConditionReason = "ConditionReasonFailedToDeleteSecret"
ConditionReasonFailedToUpdateSecret ConditionReason = "FailedToUpdateSecret"
ConditionReasonFailedToGetKubeconfig ConditionReason = "FailedToGetKubeconfig"
)
Expand Down
94 changes: 68 additions & 26 deletions internal/controller/gardener_cluster_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -83,10 +83,10 @@ func (controller *GardenerClusterController) Reconcile(ctx context.Context, req

var cluster imv1.GardenerCluster

err := controller.Client.Get(ctx, req.NamespacedName, &cluster)
err := controller.Get(ctx, req.NamespacedName, &cluster)
if err != nil {
if k8serrors.IsNotFound(err) {
err = controller.deleteKubeconfigSecret(req.NamespacedName.Name)
err = controller.deleteKubeconfigSecret(req.Name)
}

if err == nil {
Expand All @@ -97,19 +97,21 @@ func (controller *GardenerClusterController) Reconcile(ctx context.Context, req
}

lastSyncTime := time.Now()
kubeconfigRotated, err := controller.createOrRotateKubeconfigSecret(ctx, &cluster, lastSyncTime)
kubeconfigStatus, err := controller.handleKubeconfig(ctx, &cluster, lastSyncTime)
if err != nil {
_ = controller.persistStatusChange(ctx, &cluster)

return controller.resultWithoutRequeue(), err
}

err = controller.removeForceRotationAnnotation(ctx, &cluster)
if err != nil {
return controller.resultWithoutRequeue(), err
// there was a request to rotate the kubeconfig
if kubeconfigStatus == ksRevoked {
err = controller.removeForceRotationAnnotation(ctx, &cluster)
if err != nil {
return controller.resultWithoutRequeue(), err
}
}

if kubeconfigRotated {
if kubeconfigStatus == ksCreated || kubeconfigStatus == ksModified {
err = controller.persistStatusChange(ctx, &cluster)
if err != nil {
return controller.resultWithoutRequeue(), err
Expand Down Expand Up @@ -145,7 +147,7 @@ func (controller *GardenerClusterController) persistStatusChange(ctx context.Con
}
var clusterToUpdate imv1.GardenerCluster

err := controller.Client.Get(ctx, key, &clusterToUpdate)
err := controller.Get(ctx, key, &clusterToUpdate)
if err != nil {
return err
}
Expand Down Expand Up @@ -185,7 +187,7 @@ func (controller *GardenerClusterController) getSecret(shootName string) (*corev
"kyma-project.io/shoot-name": shootName,
})

err := controller.Client.List(context.Background(), &secretList, shootNameSelector)
err := controller.List(context.Background(), &secretList, shootNameSelector)
if err != nil {
return nil, err
}
Expand All @@ -203,35 +205,52 @@ func (controller *GardenerClusterController) getSecret(shootName string) (*corev
return &secretList.Items[0], nil
}

func (controller *GardenerClusterController) createOrRotateKubeconfigSecret(ctx context.Context, cluster *imv1.GardenerCluster, lastSyncTime time.Time) (bool, error) {
type kubeconfigStatus int

const (
ksZero kubeconfigStatus = iota
ksCreated
ksModified
ksRevoked
)

func (controller *GardenerClusterController) handleKubeconfig(ctx context.Context, cluster *imv1.GardenerCluster, lastSyncTime time.Time) (kubeconfigStatus, error) {
existingSecret, err := controller.getSecret(cluster.Spec.Shoot.Name)
if err != nil && !k8serrors.IsNotFound(err) {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToGetSecret, metav1.ConditionTrue, err)
return true, err
return ksZero, err
}

if !secretNeedsToBeRotated(cluster, existingSecret, controller.rotationPeriod) {
message := fmt.Sprintf("Secret %s in namespace %s does not need to be rotated yet.", cluster.Spec.Kubeconfig.Secret.Name, cluster.Spec.Kubeconfig.Secret.Namespace)
controller.log.Info(message, loggingContextFromCluster(cluster)...)
return false, nil
kubeconfig, err := controller.KubeconfigProvider.Fetch(cluster.Spec.Shoot.Name)
if err != nil {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToGetKubeconfig, metav1.ConditionTrue, err)
return ksZero, err
}

if secretRotationForced(cluster) {
message := fmt.Sprintf("Rotation of secret %s in namespace %s forced.", cluster.Spec.Kubeconfig.Secret.Name, cluster.Spec.Kubeconfig.Secret.Namespace)
controller.log.Info(message, loggingContextFromCluster(cluster)...)

// delete secret containing kubeconfig to be rotated
if err := controller.removeKubeconfig(ctx, cluster, existingSecret); err != nil {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToDeleteSecret, metav1.ConditionTrue, err)
return ksZero, err
}

return ksRevoked, nil
}

kubeconfig, err := controller.KubeconfigProvider.Fetch(cluster.Spec.Shoot.Name)
if err != nil {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToGetKubeconfig, metav1.ConditionTrue, err)
return true, err
if !secretNeedsToBeRotated(cluster, existingSecret, controller.rotationPeriod) {
message := fmt.Sprintf("Secret %s in namespace %s does not need to be rotated yet.", cluster.Spec.Kubeconfig.Secret.Name, cluster.Spec.Kubeconfig.Secret.Namespace)
controller.log.Info(message, loggingContextFromCluster(cluster)...)
return ksZero, nil
}

if existingSecret != nil {
return true, controller.updateExistingSecret(ctx, kubeconfig, cluster, existingSecret, lastSyncTime)
return ksModified, controller.updateExistingSecret(ctx, kubeconfig, cluster, existingSecret, lastSyncTime)
}

return true, controller.createNewSecret(ctx, kubeconfig, cluster, lastSyncTime)
return ksCreated, controller.createNewSecret(ctx, kubeconfig, cluster, lastSyncTime)
}

func secretNeedsToBeRotated(cluster *imv1.GardenerCluster, secret *corev1.Secret, rotationPeriod time.Duration) bool {
Expand Down Expand Up @@ -271,16 +290,22 @@ func secretRotationForced(cluster *imv1.GardenerCluster) bool {
}

_, found := annotations[forceKubeconfigRotationAnnotation]

return found
}

func (controller *GardenerClusterController) deleteSecret(ctx context.Context, secret *corev1.Secret) error {

Check failure on line 296 in internal/controller/gardener_cluster_controller.go

View workflow job for this annotation

GitHub Actions / lint

func `(*GardenerClusterController).deleteSecret` is unused (unused)
err := controller.Delete(ctx, secret)
if k8serrors.IsNotFound(err) {
return nil
}
return err
}

func (controller *GardenerClusterController) createNewSecret(ctx context.Context, kubeconfig string, cluster *imv1.GardenerCluster, lastSyncTime time.Time) error {
newSecret := controller.newSecret(*cluster, kubeconfig, lastSyncTime)
err := controller.Client.Create(ctx, &newSecret)
err := controller.Create(ctx, &newSecret)
if err != nil {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToCreateSecret, metav1.ConditionTrue, err)

return err
}

Expand All @@ -292,7 +317,24 @@ func (controller *GardenerClusterController) createNewSecret(ctx context.Context
return nil
}

func (controller *GardenerClusterController) removeKubeconfig(ctx context.Context, cluster *imv1.GardenerCluster, existingSecret *corev1.Secret) error {
if existingSecret == nil {
return nil
}

delete(existingSecret.Data, cluster.Spec.Kubeconfig.Secret.Key)

if annotations := existingSecret.GetAnnotations(); annotations != nil {
delete(annotations, lastKubeconfigSyncAnnotation)
}

return controller.Update(ctx, existingSecret)
}

func (controller *GardenerClusterController) updateExistingSecret(ctx context.Context, kubeconfig string, cluster *imv1.GardenerCluster, existingSecret *corev1.Secret, lastSyncTime time.Time) error {
if existingSecret.Data == nil {
existingSecret.Data = map[string][]byte{}
}
existingSecret.Data[cluster.Spec.Kubeconfig.Secret.Key] = []byte(kubeconfig)
annotations := existingSecret.GetAnnotations()
if annotations == nil {
Expand All @@ -302,7 +344,7 @@ func (controller *GardenerClusterController) updateExistingSecret(ctx context.Co
annotations[lastKubeconfigSyncAnnotation] = lastSyncTime.UTC().Format(time.RFC3339)
existingSecret.SetAnnotations(annotations)

err := controller.Client.Update(ctx, existingSecret)
err := controller.Update(ctx, existingSecret)
if err != nil {
cluster.UpdateConditionForErrorState(imv1.ConditionTypeKubeconfigManagement, imv1.ConditionReasonFailedToUpdateSecret, metav1.ConditionTrue, err)

Expand Down

0 comments on commit 93651ec

Please sign in to comment.