Skip to content

Commit

Permalink
add DeleteDatabaseAndAccountdFinalizers
Browse files Browse the repository at this point in the history
the current approach of removing finalizers is dependent on
getting at a MariaDBDatabase and a complete MariaDBAccount with a
Secret at the
same time to produce a Database object.  At that point, the finalizers
are removed from the sub-elements.   however if the MariaDBAccount
or MariaDBDatabase is missing then nothing gets removed, this is a
bug.  So add new function that looks up all three types of objects
independently of each other and remove finalizers from each, regardless
of which are found or not.
  • Loading branch information
zzzeek committed Sep 17, 2024
1 parent a06f656 commit 8598d28
Showing 1 changed file with 86 additions and 9 deletions.
95 changes: 86 additions & 9 deletions api/v1beta1/mariadbdatabase_funcs.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ import (

k8s_errors "k8s.io/apimachinery/pkg/api/errors"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/types"
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 @@ -362,7 +361,6 @@ func (d *Database) loadDatabaseAndAccountCRs(
ctx context.Context,
h *helper.Helper,
) error {
mariaDBDatabase := &MariaDBDatabase{}
name := d.name
namespace := d.namespace
accountName := d.accountName
Expand All @@ -384,13 +382,7 @@ func (d *Database) loadDatabaseAndAccountCRs(
)
}

err := h.GetClient().Get(
ctx,
types.NamespacedName{
Name: name,
Namespace: namespace,
},
mariaDBDatabase)
mariaDBDatabase, err := GetDatabase(ctx, h, name, namespace)

if err != nil {
if k8s_errors.IsNotFound(err) {
Expand Down Expand Up @@ -532,6 +524,71 @@ func (d *Database) GetDatabaseClientConfig(s *tls.Service) string {
return strings.Join(conn, "\n")
}

// DeleteDatabaseAndAccountFinalizers performs the same tasks as
// GetDatabaseByNameAndAccount and then database.DeleteFinalizer, but does
// so such that all individual objects that exist are guaranteed to be updated,
// even if other objects in the Database combination don't exist. This
// includes the MariaDBDatabase, all MariaDBAccount objects and their
// associated Secret objects.
func DeleteDatabaseAndAccountFinalizers(
ctx context.Context,
h *helper.Helper,
name string,
accountName string,
namespace string,
) error {

databaseAccount, err := GetAccount(ctx, h, accountName, namespace)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
} else if err == nil {
if databaseAccount.Spec.Secret != "" {
dbSecret, _, err := secret.GetSecret(ctx, h, databaseAccount.Spec.Secret, namespace)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
}

if err == nil && controllerutil.RemoveFinalizer(dbSecret, h.GetFinalizer()) {
err := h.GetClient().Update(ctx, dbSecret)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
}
util.LogForObject(h, fmt.Sprintf("Removed finalizer %s from Secret %s", h.GetFinalizer(), dbSecret.Name), dbSecret)
}
}

if controllerutil.RemoveFinalizer(databaseAccount, h.GetFinalizer()) {
err := h.GetClient().Update(ctx, databaseAccount)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
}
util.LogForObject(h, fmt.Sprintf("Removed finalizer %s from MariaDBAccount %s", h.GetFinalizer(), databaseAccount.Name), databaseAccount)
}
}

// also do a delete for "unused" MariaDBAccounts, associated with
// this MariaDBDatabase.
err = DeleteUnusedMariaDBAccountFinalizers(
ctx, h, name, accountName, namespace,
)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
}

mariaDBDatabase, err := GetDatabase(ctx, h, name, namespace)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
} else if err == nil && controllerutil.RemoveFinalizer(mariaDBDatabase, h.GetFinalizer()) {
err := h.GetClient().Update(ctx, mariaDBDatabase)
if err != nil && !k8s_errors.IsNotFound(err) {
return err
}
util.LogForObject(h, fmt.Sprintf("Removed finalizer %s from MariaDBDatabase %s", h.GetFinalizer(), mariaDBDatabase.Spec.Name), mariaDBDatabase)
}

return nil
}

// DeleteUnusedMariaDBAccountFinalizers searches for all MariaDBAccounts
// associated with the given MariaDBDatabase name and removes the finalizer for all
// of them except for the given named account.
Expand Down Expand Up @@ -669,6 +726,26 @@ func createOrPatchAccountAndSecret(
return opAcc, errAcc
}

// GetDatabase returns an existing MariaDBDatabase object from the cluster
func GetDatabase(ctx context.Context,
h *helper.Helper,
name string, namespace string,
) (*MariaDBDatabase, error) {
mariaDBDatabase := &MariaDBDatabase{
ObjectMeta: metav1.ObjectMeta{
Name: name,
Namespace: namespace,
},
}
objectKey := client.ObjectKeyFromObject(mariaDBDatabase)

err := h.GetClient().Get(ctx, objectKey, mariaDBDatabase)
if err != nil {
return nil, err
}
return mariaDBDatabase, err
}

// GetAccount returns an existing MariaDBAccount object from the cluster
func GetAccount(ctx context.Context,
h *helper.Helper,
Expand Down

0 comments on commit 8598d28

Please sign in to comment.