From 5fb91d35d0ecc86b4f99aa94796834aa7b3726f2 Mon Sep 17 00:00:00 2001 From: HarshwardhanPatil07 Date: Thu, 6 Aug 2026 10:36:30 +0530 Subject: [PATCH] Fix CoreDNS readiness race in integration test Wait for CoreDNS pods to be ready before attempting DNS resolution, preventing flaky "Connection refused" failures. Signed-off-by: HarshwardhanPatil07 --- internal/cluster/init.go | 7 +++++++ internal/kube/resources.go | 25 +++++++++++++++++++++++++ 2 files changed, 32 insertions(+) diff --git a/internal/cluster/init.go b/internal/cluster/init.go index 69c2aca..26acf3d 100644 --- a/internal/cluster/init.go +++ b/internal/cluster/init.go @@ -152,6 +152,13 @@ func (c *Cluster) Init(ctx context.Context, opts InitOptions) error { return fmt.Errorf("failed to patch CoreDNS: %w", err) } + c.logger.Info("") + c.logger.Info("Waiting for CoreDNS to be ready...") + if err := kubeClient.WaitForDeploymentReady(ctx, "kube-system", "coredns", 3*time.Minute); err != nil { + return fmt.Errorf("CoreDNS not ready: %w", err) + } + c.logger.Info("✓ CoreDNS is ready") + c.logger.Info("") c.logger.Infof("✅ Cluster initialized on %s with Calico CNI", nodeName) diff --git a/internal/kube/resources.go b/internal/kube/resources.go index b10e2cb..e45f3fd 100644 --- a/internal/kube/resources.go +++ b/internal/kube/resources.go @@ -156,6 +156,31 @@ func (c *Client) EnableCoreDNSFallthrough(ctx context.Context) error { return nil } +// WaitForDeploymentReady polls until the named deployment has at least one +// ready replica, or the timeout expires. +func (c *Client) WaitForDeploymentReady(ctx context.Context, namespace, name string, timeout time.Duration) error { + deadline := time.After(timeout) + ticker := time.NewTicker(2 * time.Second) + defer ticker.Stop() + + for { + select { + case <-ctx.Done(): + return ctx.Err() + case <-deadline: + return fmt.Errorf("timed out waiting for deployment %s/%s to be ready", namespace, name) + case <-ticker.C: + deploy, err := c.clientset.AppsV1().Deployments(namespace).Get(ctx, name, metav1.GetOptions{}) + if err != nil { + continue + } + if deploy.Status.ReadyReplicas >= 1 { + return nil + } + } + } +} + // LabelNode adds the given labels to a node, overwriting any that already exist. func (c *Client) LabelNode(ctx context.Context, nodeName string, labels map[string]string) error { patch := map[string]interface{}{