diff --git a/hack/run-fmt.sh b/hack/run-fmt.sh index edf3f74..d1146a2 100755 --- a/hack/run-fmt.sh +++ b/hack/run-fmt.sh @@ -43,7 +43,7 @@ fi GOIMPORTS="${GOIMPORTS:-$(pwd)/bin/goimports}" # Run go fmt. -go fmt ./... +go fmt ./cmd/... $(go list -f "{{.Dir}}" ./pkg/... | grep -v pkg/generated) # Run goimports to sort imports. # Do not sort generated files. diff --git a/pkg/cli/cmd/common.go b/pkg/cli/cmd/common.go index 151eb2f..60bcc3f 100644 --- a/pkg/cli/cmd/common.go +++ b/pkg/cli/cmd/common.go @@ -60,8 +60,7 @@ func NewContext(_ *cobra.Command) (controllercontext.Context, error) { // PrerunWithKubeconfig is a pre-run function that will set up the common context when kubeconfig is needed. // TODO(irvinlim): We currently reuse controllercontext, but most of it is unusable for CLI interfaces. -// -// We should create a new common context as needed. +// We should create a new common context as needed. func PrerunWithKubeconfig(cmd *cobra.Command, _ []string) error { // Already set up previously. if ctrlContext != nil { @@ -95,9 +94,8 @@ func GetNamespace(cmd *cobra.Command) (string, error) { // GetDynamicConfig loads the dynamic config by name and unmarshals to out. // TODO(irvinlim): If the current user does not have permissions to read the -// -// ConfigMap, or the ConfigMap uses a different name/namespace, we should -// gracefully handle this case. +// ConfigMap, or the ConfigMap uses a different name/namespace, we should +// gracefully handle this case. func GetDynamicConfig(ctx context.Context, cmd *cobra.Command, name configv1alpha1.ConfigName, out interface{}) error { cfgNamespace, err := cmd.Flags().GetString("dynamic-config-namespace") if err != nil { diff --git a/pkg/runtime/testing/fixture.go b/pkg/runtime/testing/fixture.go index 9aaf075..3b2a830 100644 --- a/pkg/runtime/testing/fixture.go +++ b/pkg/runtime/testing/fixture.go @@ -41,7 +41,7 @@ func InitFixtures(ctx context.Context, client controllercontext.Clientsets, fixt // InitFixture initializes a single fixture against a clientset. // TODO(irvinlim): Currently we just hardcode a list of types to be initialized, -// we could probably use reflection instead. +// we could probably use reflection instead. func InitFixture(ctx context.Context, client controllercontext.Clientsets, fixture runtime.Object) error { var err error switch f := fixture.(type) { diff --git a/pkg/runtime/testing/reconciler.go b/pkg/runtime/testing/reconciler.go index b74b06c..8fbb98a 100644 --- a/pkg/runtime/testing/reconciler.go +++ b/pkg/runtime/testing/reconciler.go @@ -33,6 +33,7 @@ import ( "github.com/furiko-io/furiko/pkg/runtime/controllercontext" "github.com/furiko-io/furiko/pkg/runtime/controllercontext/mock" + "github.com/furiko-io/furiko/pkg/runtime/controllerutil" "github.com/furiko-io/furiko/pkg/runtime/reconciler" "github.com/furiko-io/furiko/pkg/utils/ktime" ) @@ -158,16 +159,16 @@ func (r *ReconcilerTest) RunTestCase(t testinginterface.T, tt ReconcilerTestCase // Initialize reconciler. recon := r.ReconcilerFunc(ctrlContext) - // Start the context. - err := c.Start(ctx) - assert.NoError(t, err) - // Initialize fixtures. target, err := r.initClientset(ctx, c.MockClientsets(), tt, ctrlContext.GetHasSynced()) if err != nil { t.Fatalf("cannot initialize fixtures: %v", err) } + // Start the context. + assert.NoError(t, c.Start(ctx)) + assert.NoError(t, r.waitForCacheSync(ctx, c.MockClientsets(), ctrlContext.GetHasSynced())) + // Trigger sync. if err := r.triggerReconcile(ctx, t, target, tt, recon); err != nil { t.Fatalf("cannot trigger reconcile: %v", err) @@ -236,17 +237,23 @@ func (r *ReconcilerTest) initClientset( client.FurikoMock().PrependReactor(reactor.Verb, reactor.Resource, reactor.React) } - // Wait for cache sync - // NOTE(irvinlim): Add a short delay otherwise cache may not sync consistently - time.Sleep(time.Millisecond * 50) - if !cache.WaitForCacheSync(ctx.Done(), hasSynced...) { - return nil, errors.New("caches not synced") + return target, nil +} + +func (r *ReconcilerTest) waitForCacheSync( + ctx context.Context, + client *mock.Clientsets, + hasSynced []cache.InformerSynced, +) error { + // Wait for cache sync. + if err := controllerutil.WaitForNamedCacheSyncWithTimeout(ctx, "TestController", time.Second, hasSynced...); err != nil { + return err } // Clear all actions prior to reconcile. client.ClearActions() - return target, nil + return nil } func (r *ReconcilerTest) triggerReconcile(