-
Notifications
You must be signed in to change notification settings - Fork 141
feat: make observe-only resources reflect diff to upstream in conditions (Synced=False) #926
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
base: main
Are you sure you want to change the base?
Changes from 9 commits
91f2363
085f996
e6748da
d3a95e6
28620eb
86ceb6e
d8085af
a21d83e
07a3348
8357484
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 |
|---|---|---|
|
|
@@ -1770,7 +1770,7 @@ func TestModernReconciler(t *testing.T) { | |
| }, | ||
| want: want{result: reconcile.Result{Requeue: true}}, | ||
| }, | ||
| "ObserveOnlySuccessfulObserve": { | ||
| "ObserveOnlySuccessfulObserveNoDiff": { | ||
| reason: "With Observe, a successful managed resource observe should trigger a requeue after a long wait.", | ||
| args: args{ | ||
| m: &fake.Manager{ | ||
|
|
@@ -1787,7 +1787,7 @@ func TestModernReconciler(t *testing.T) { | |
| want.SetConditions(xpv1.ReconcileSuccess().WithObservedGeneration(42).WithObservedGeneration(42)) | ||
|
|
||
| if diff := cmp.Diff(want, obj, test.EquateConditions()); diff != "" { | ||
| reason := "With ObserveOnly, a successful managed resource observation should be reported as a conditioned status." | ||
| reason := "With ObserveOnly, a successful managed resource observation without any diff between external resource and desired spec should be reported as a conditioned status." | ||
| t.Errorf("\nReason: %s\n-want, +got:\n%s", reason, diff) | ||
| } | ||
|
|
||
|
|
@@ -1803,7 +1803,7 @@ func TestModernReconciler(t *testing.T) { | |
| WithExternalConnector(ExternalConnectorFn(func(_ context.Context, _ resource.Managed) (ExternalClient, error) { | ||
| c := &ExternalClientFns{ | ||
| ObserveFn: func(_ context.Context, _ resource.Managed) (ExternalObservation, error) { | ||
| return ExternalObservation{ResourceExists: true}, nil | ||
| return ExternalObservation{ResourceExists: true, ResourceUpToDate: true}, nil | ||
| }, | ||
| DisconnectFn: func(_ context.Context) error { | ||
| return nil | ||
|
|
@@ -2032,8 +2032,8 @@ func TestModernReconciler(t *testing.T) { | |
| }, | ||
| want: want{result: reconcile.Result{Requeue: false}}, | ||
| }, | ||
| "ManagementPolicyImmutable": { | ||
| reason: "Successful reconciliation skipping update should trigger a requeue after a long wait.", | ||
| "ManagementPolicyImmutableNoDiff": { | ||
| reason: "Successful reconciliation without upstream diff and skipping update should trigger a requeue after a long wait", | ||
| args: args{ | ||
| m: &fake.Manager{ | ||
| Client: &test.MockClient{ | ||
|
|
@@ -2050,7 +2050,7 @@ func TestModernReconciler(t *testing.T) { | |
| want.SetConditions(xpv1.ReconcileSuccess().WithObservedGeneration(42)) | ||
|
|
||
| if diff := cmp.Diff(want, obj, test.EquateConditions()); diff != "" { | ||
| reason := `Managed resource should acquire Synced=False/ReconcileSuccess status condition.` | ||
| reason := `Managed resource should acquire Synced=True/ReconcileSuccess status condition.` | ||
| t.Errorf("\nReason: %s\n-want, +got:\n%s", reason, diff) | ||
| } | ||
|
|
||
|
|
@@ -2067,7 +2067,59 @@ func TestModernReconciler(t *testing.T) { | |
| WithExternalConnector(ExternalConnectorFn(func(_ context.Context, _ resource.Managed) (ExternalClient, error) { | ||
| c := &ExternalClientFns{ | ||
| ObserveFn: func(_ context.Context, _ resource.Managed) (ExternalObservation, error) { | ||
| return ExternalObservation{ResourceExists: true, ResourceUpToDate: false}, nil | ||
| return ExternalObservation{ResourceExists: true, ResourceUpToDate: true}, nil | ||
| }, | ||
| UpdateFn: func(_ context.Context, _ resource.Managed) (ExternalUpdate, error) { | ||
| return ExternalUpdate{}, errBoom | ||
| }, | ||
| DisconnectFn: func(_ context.Context) error { | ||
| return nil | ||
| }, | ||
| } | ||
|
|
||
| return c, nil | ||
| })), | ||
| WithFinalizer(resource.FinalizerFns{AddFinalizerFn: func(_ context.Context, _ resource.Object) error { return nil }}), | ||
| }, | ||
| }, | ||
| want: want{result: reconcile.Result{RequeueAfter: defaultPollInterval}}, | ||
| }, | ||
| "ManagementPolicyImmutableWithDiff": { | ||
| reason: "Successful reconciliation with upstream diff and skipping update should trigger a requeue after a long wait.", | ||
| args: args{ | ||
| m: &fake.Manager{ | ||
| Client: &test.MockClient{ | ||
| MockGet: test.NewMockGetFn(nil, func(obj client.Object) error { | ||
| mg := asModernManaged(obj, 42) | ||
| mg.SetManagementPolicies(xpv1.ManagementPolicies{xpv1.ManagementActionObserve, xpv1.ManagementActionLateInitialize, xpv1.ManagementActionCreate, xpv1.ManagementActionDelete}) | ||
|
|
||
| return nil | ||
| }), | ||
| MockUpdate: test.NewMockUpdateFn(errBoom), | ||
| MockStatusUpdate: test.MockSubResourceUpdateFn(func(_ context.Context, obj client.Object, _ ...client.SubResourceUpdateOption) error { | ||
| want := newModernManaged(42) | ||
| want.SetManagementPolicies(xpv1.ManagementPolicies{xpv1.ManagementActionObserve, xpv1.ManagementActionLateInitialize, xpv1.ManagementActionCreate, xpv1.ManagementActionDelete}) | ||
| want.SetConditions(xpv1.ReconcileForbidden().WithObservedGeneration(42).WithMessage("External resource differs from desired state, but will not update due to missing 'Update' managementPolicy. Diff:\nmock diff")) | ||
|
|
||
| if diff := cmp.Diff(want, obj, test.EquateConditions()); diff != "" { | ||
| reason := `Managed resource should acquire Synced=False/ReconcileForbidden status condition.` | ||
coderabbitai[bot] marked this conversation as resolved.
Show resolved
Hide resolved
Comment on lines
+2088
to
+2105
Contributor
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. Reword the case reason to match ReconcileForbidden. This test expects Suggested edit- reason: "Successful reconciliation with upstream diff and skipping update should trigger a requeue after a long wait.",
+ reason: "Reconciliation with upstream diff and no update permission should set ReconcileForbidden and requeue.",As per coding guidelines, “Check for proper test case naming and reason fields.” 🤖 Prompt for AI Agents |
||
| t.Errorf("\nReason: %s\n-want, +got:\n%s", reason, diff) | ||
| } | ||
|
|
||
| return nil | ||
| }), | ||
| }, | ||
| Scheme: fake.SchemeWith(&fake.ModernManaged{}), | ||
| }, | ||
| mg: resource.ManagedKind(fake.GVK(&fake.ModernManaged{})), | ||
| o: []ReconcilerOption{ | ||
| WithInitializers(), | ||
| WithManagementPolicies(), | ||
| WithReferenceResolver(ReferenceResolverFn(func(_ context.Context, _ resource.Managed) error { return nil })), | ||
| WithExternalConnector(ExternalConnectorFn(func(_ context.Context, _ resource.Managed) (ExternalClient, error) { | ||
| c := &ExternalClientFns{ | ||
| ObserveFn: func(_ context.Context, _ resource.Managed) (ExternalObservation, error) { | ||
| return ExternalObservation{ResourceExists: true, ResourceUpToDate: false, Diff: "mock diff"}, nil | ||
| }, | ||
| UpdateFn: func(_ context.Context, _ resource.Managed) (ExternalUpdate, error) { | ||
| return ExternalUpdate{}, errBoom | ||
|
|
||
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.
Reason text says “Sync Paused,” but expected condition is ReconcileForbidden.
Could we update the case reason to match the actual condition being asserted? It’ll make failures far easier to interpret.
Suggested edit
As per coding guidelines, “Check for proper test case naming and reason fields.”
📝 Committable suggestion
🤖 Prompt for AI Agents