-
Notifications
You must be signed in to change notification settings - Fork 15
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
feat: handle UID mismatch between incoming and existing resources #242
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -55,13 +55,36 @@ func (a *Agent) processIncomingApplication(ev *event.Event) error { | |
return err | ||
} | ||
|
||
sourceUIDMatch, err := a.appManager.CompareSourceUID(a.context, incomingApp) | ||
if err != nil { | ||
return fmt.Errorf("failed to compare the source UID of app: %w", err) | ||
} | ||
|
||
switch ev.Type() { | ||
case event.Create: | ||
if !sourceUIDMatch { | ||
logCtx.Debug("An app already exists with a different source UID. Deleting the existing app") | ||
if err := a.deleteApplication(incomingApp); err != nil { | ||
return err | ||
} | ||
} | ||
|
||
_, err = a.createApplication(incomingApp) | ||
if err != nil { | ||
logCtx.Errorf("Error creating application: %v", err) | ||
} | ||
case event.SpecUpdate: | ||
if !sourceUIDMatch { | ||
logCtx.Debug("Source UID mismatch between the incoming app and existing app. Deleting the existing app") | ||
if err := a.deleteApplication(incomingApp); err != nil { | ||
return err | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same about augmenting the error as above. |
||
} | ||
|
||
logCtx.Debug("Creating the incoming app after deleting the existing app") | ||
_, err := a.createApplication(incomingApp) | ||
return err | ||
} | ||
|
||
_, err = a.updateApplication(incomingApp) | ||
if err != nil { | ||
logCtx.Errorf("Error updating application: %v", err) | ||
|
@@ -87,13 +110,36 @@ func (a *Agent) processIncomingAppProject(ev *event.Event) error { | |
return err | ||
} | ||
|
||
sourceUIDMatch, err := a.projectManager.CompareSourceUID(a.context, incomingAppProject) | ||
if err != nil { | ||
return fmt.Errorf("failed to validate source UID of appProject: %w", err) | ||
} | ||
|
||
switch ev.Type() { | ||
case event.Create: | ||
if !sourceUIDMatch { | ||
logCtx.Debug("An appProject already exists with a different source UID. Deleting the existing appProject") | ||
if err := a.deleteAppProject(incomingAppProject); err != nil { | ||
return err | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same about augmenting the error as above. |
||
} | ||
} | ||
|
||
_, err = a.createAppProject(incomingAppProject) | ||
if err != nil { | ||
logCtx.Errorf("Error creating appproject: %v", err) | ||
} | ||
case event.SpecUpdate: | ||
if !sourceUIDMatch { | ||
logCtx.Debug("Source UID mismatch between the incoming and existing appProject. Deleting the existing appProject") | ||
if err := a.deleteAppProject(incomingAppProject); err != nil { | ||
return err | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same about augmenting the error as above. |
||
} | ||
|
||
logCtx.Debug("Creating the incoming appProject after deleting the existing appProject") | ||
_, err := a.createAppProject(incomingAppProject) | ||
return err | ||
} | ||
|
||
_, err = a.updateAppProject(incomingAppProject) | ||
if err != nil { | ||
logCtx.Errorf("Error updating appproject: %v", err) | ||
|
@@ -153,13 +199,13 @@ func (a *Agent) createApplication(incoming *v1alpha1.Application) (*v1alpha1.App | |
} | ||
|
||
func (a *Agent) updateApplication(incoming *v1alpha1.Application) (*v1alpha1.Application, error) { | ||
// | ||
incoming.ObjectMeta.SetNamespace(a.namespace) | ||
logCtx := log().WithFields(logrus.Fields{ | ||
"method": "UpdateApplication", | ||
"app": incoming.QualifiedName(), | ||
"resourceVersion": incoming.ResourceVersion, | ||
}) | ||
|
||
if a.appManager.IsChangeIgnored(incoming.QualifiedName(), incoming.ResourceVersion) { | ||
logCtx.Tracef("Discarding this event, because agent has seen this version %s already", incoming.ResourceVersion) | ||
return nil, event.NewEventDiscardedErr("the version %s has already been seen by this agent", incoming.ResourceVersion) | ||
|
@@ -262,6 +308,7 @@ func (a *Agent) updateAppProject(incoming *v1alpha1.AppProject) (*v1alpha1.AppPr | |
"app": incoming.Name, | ||
"resourceVersion": incoming.ResourceVersion, | ||
}) | ||
|
||
if a.appManager.IsChangeIgnored(incoming.Name, incoming.ResourceVersion) { | ||
logCtx.Tracef("Discarding this event, because agent has seen this version %s already", incoming.ResourceVersion) | ||
return nil, event.NewEventDiscardedErr("the version %s has already been seen by this agent", incoming.ResourceVersion) | ||
|
@@ -287,7 +334,7 @@ func (a *Agent) deleteAppProject(project *v1alpha1.AppProject) error { | |
// means that we're out-of-sync from the control plane. | ||
// | ||
// TODO(jannfis): Handle this situation properly instead of throwing an error. | ||
if !a.appManager.IsManaged(project.Name) { | ||
if !a.projectManager.IsManaged(project.Name) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 👍 |
||
return fmt.Errorf("appProject %s is not managed", project.Name) | ||
} | ||
|
||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we should give more context to the returned error here.
The caller will expect an application to be created, and probably reflect that in any error message logged, but could potentially receive an error from the delete operation.
For example, the following case would be confusing (admittedly, the chance for this happening is very slim, but it should ):
sourceUIDMatch
is falsea.deleteApplication
fails because the resource already is deleted. The error would be "the requested resource could not be found"Or think about RBAC - agent might have RBAC to create applications, but not delete applications, but the create call would return a permission denied. Troubleshooting that would be fun :)
So it would make more sense to augment the returned error by more information, e.g.
fmt.Errorf("could not delete existing resource prior to creation: %w", err)
or something similar.