Skip to content

[fix] handle requeues for linode api errors on update and delete, set instance ID if linode already exists #408

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Jul 16, 2024
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
1 change: 0 additions & 1 deletion cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -175,7 +175,6 @@ func main() {
if err = reconciler.NewReconcilerWithTracing(
&controller.LinodeMachineReconciler{
Client: mgr.GetClient(),
Scheme: mgr.GetScheme(),
Recorder: mgr.GetEventRecorderFor("LinodeMachineReconciler"),
WatchFilterValue: machineWatchFilter,
LinodeApiKey: linodeToken,
Expand Down
42 changes: 22 additions & 20 deletions controller/linodemachine_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,6 @@
corev1 "k8s.io/api/core/v1"
apierrors "k8s.io/apimachinery/pkg/api/errors"
"k8s.io/apimachinery/pkg/api/resource"
"k8s.io/apimachinery/pkg/runtime"
utilerrors "k8s.io/apimachinery/pkg/util/errors"
"k8s.io/client-go/tools/record"
clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1"
Expand Down Expand Up @@ -95,7 +94,6 @@
LinodeApiKey string
LinodeDNSAPIKey string
WatchFilterValue string
Scheme *runtime.Scheme
ReconcileTimeout time.Duration
}

Expand Down Expand Up @@ -215,9 +213,7 @@
}
}

err = r.reconcileDelete(ctx, logger, machineScope)

return
return r.reconcileDelete(ctx, logger, machineScope)

Check warning on line 216 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L216

Added line #L216 was not covered by tests
}

linodeClusterKey := client.ObjectKey{
Expand Down Expand Up @@ -307,7 +303,6 @@

return ctrl.Result{}, err
}

linodeInstance, err = machineScope.LinodeClient.CreateInstance(ctx, *createOpts)
if err != nil {
if linodego.ErrHasStatus(err, linodeTooManyRequests) || linodego.ErrHasStatus(err, linodego.ErrorFromError) {
Expand All @@ -324,17 +319,16 @@

return ctrl.Result{RequeueAfter: reconciler.DefaultMachineControllerWaitForRunningDelay}, nil
}

conditions.MarkTrue(machineScope.LinodeMachine, ConditionPreflightCreated)
machineScope.LinodeMachine.Spec.InstanceID = &linodeInstance.ID

default:
err = errors.New("multiple instances")
logger.Error(err, "multiple instances found", "tags", tags)

return ctrl.Result{}, err
}

conditions.MarkTrue(machineScope.LinodeMachine, ConditionPreflightCreated)
machineScope.LinodeMachine.Spec.InstanceID = &linodeInstance.ID

return r.reconcileInstanceCreate(ctx, logger, machineScope, linodeInstance)
}

Expand Down Expand Up @@ -638,6 +632,8 @@
if linodeInstance, err = machineScope.LinodeClient.GetInstance(ctx, *machineScope.LinodeMachine.Spec.InstanceID); err != nil {
if util.IgnoreLinodeAPIError(err, http.StatusNotFound) != nil {
logger.Error(err, "Failed to get Linode machine instance")

return ctrl.Result{RequeueAfter: reconciler.DefaultMachineControllerRetryDelay}, nil, err

Check warning on line 636 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L636

Added line #L636 was not covered by tests
} else {
logger.Info("Instance not found, let's create a new one")

Expand All @@ -656,12 +652,12 @@
}
if _, ok := requeueInstanceStatuses[linodeInstance.Status]; ok {
if linodeInstance.Updated.Add(reconciler.DefaultMachineControllerWaitForRunningTimeout).After(time.Now()) {
logger.Info("Instance has one operaton running, re-queuing reconciliation", "status", linodeInstance.Status)
logger.Info("Instance has one operation running, re-queuing reconciliation", "status", linodeInstance.Status)

Check warning on line 655 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L655

Added line #L655 was not covered by tests

return ctrl.Result{RequeueAfter: reconciler.DefaultMachineControllerWaitForRunningDelay}, linodeInstance, nil
}

logger.Info("Instance has one operaton long running, skipping reconciliation", "status", linodeInstance.Status)
logger.Info("Instance has one operation long running, skipping reconciliation", "status", linodeInstance.Status)

Check warning on line 660 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L660

Added line #L660 was not covered by tests

conditions.MarkFalse(machineScope.LinodeMachine, clusterv1.ReadyCondition, string(linodeInstance.Status), clusterv1.ConditionSeverityInfo, "skipped due to long running operation")

Expand All @@ -685,30 +681,36 @@
ctx context.Context,
logger logr.Logger,
machineScope *scope.MachineScope,
) error {
) (ctrl.Result, error) {
logger.Info("deleting machine")

if machineScope.LinodeMachine.Spec.InstanceID == nil {
logger.Info("Machine ID is missing, nothing to do")

if err := machineScope.RemoveCredentialsRefFinalizer(ctx); err != nil {
logger.Error(err, "Failed to update credentials secret")
return err
return ctrl.Result{}, err

Check warning on line 692 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L692

Added line #L692 was not covered by tests
}
controllerutil.RemoveFinalizer(machineScope.LinodeMachine, infrav1alpha1.MachineFinalizer)

return nil
return ctrl.Result{}, nil

Check warning on line 696 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L696

Added line #L696 was not covered by tests
}

if err := r.removeMachineFromLB(ctx, logger, machineScope); err != nil {
return fmt.Errorf("remove machine from loadbalancer: %w", err)
return ctrl.Result{}, fmt.Errorf("remove machine from loadbalancer: %w", err)

Check warning on line 700 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L700

Added line #L700 was not covered by tests
}

if err := machineScope.LinodeClient.DeleteInstance(ctx, *machineScope.LinodeMachine.Spec.InstanceID); err != nil {
if util.IgnoreLinodeAPIError(err, http.StatusNotFound) != nil {
logger.Error(err, "Failed to delete Linode machine instance")
logger.Error(err, "Failed to delete Linode instance")

return err
if machineScope.LinodeMachine.ObjectMeta.DeletionTimestamp.Add(reconciler.DefaultTimeout(r.ReconcileTimeout, reconciler.DefaultMachineControllerRetryDelay)).After(time.Now()) {
logger.Info("re-queuing Linode instance deletion")

return ctrl.Result{RequeueAfter: reconciler.DefaultMachineControllerRetryDelay}, nil
}

return ctrl.Result{}, err
}
}

Expand All @@ -722,15 +724,15 @@

if err := machineScope.RemoveCredentialsRefFinalizer(ctx); err != nil {
logger.Error(err, "Failed to update credentials secret")
return err
return ctrl.Result{}, err

Check warning on line 727 in controller/linodemachine_controller.go

View check run for this annotation

Codecov / codecov/patch

controller/linodemachine_controller.go#L727

Added line #L727 was not covered by tests
}
controllerutil.RemoveFinalizer(machineScope.LinodeMachine, infrav1alpha1.MachineFinalizer)
// TODO: remove this check and removal later
if controllerutil.ContainsFinalizer(machineScope.LinodeMachine, infrav1alpha1.GroupVersion.String()) {
controllerutil.RemoveFinalizer(machineScope.LinodeMachine, infrav1alpha1.GroupVersion.String())
}

return nil
return ctrl.Result{}, nil
}

// SetupWithManager sets up the controller with the Manager.
Expand Down
Loading
Loading