Sort render inputs so config is deterministic (stop restart loop)
client.List returns cache-ordered (non-deterministic) results, so the forward zones (and DNSSEC policies) reshuffled between reconciles. Before the config-hash change this was harmless, but now a reshuffled render rewrites the ConfigMap, flips the pod-template config hash, and the StatefulSet rolls forever (observed: resolver forward zones churn every reconcile, pod endlessly recreated). Sort every list rendered into named.conf (ACLs, views, forward zones, policies, DNSSEC policies) before rendering, so identical inputs always produce byte-identical config and the hash is stable.
This commit is contained in:
@@ -146,3 +146,34 @@ func TestCatalogHashStable(t *testing.T) {
|
||||
t.Fatalf("expected 40-char hex sha1, got %d: %s", len(h1), h1)
|
||||
}
|
||||
}
|
||||
|
||||
func TestRenderDeterministicWithShuffledForwards(t *testing.T) {
|
||||
// client.List order is non-deterministic; the render must not depend on
|
||||
// input order, or the ConfigMap churns and (with the config hash) the
|
||||
// StatefulSet rolls forever.
|
||||
mkFwd := func(zone, fwd string) bindv1alpha1.BindZone {
|
||||
return bindv1alpha1.BindZone{
|
||||
ObjectMeta: metav1.ObjectMeta{Name: zone},
|
||||
Spec: bindv1alpha1.BindZoneSpec{
|
||||
ClusterRef: "r", Type: bindv1alpha1.ZoneForward,
|
||||
ZoneName: zone, Forwarders: []string{fwd},
|
||||
},
|
||||
}
|
||||
}
|
||||
base := RenderInput{Cluster: newCluster(bindv1alpha1.ModeResolver)}
|
||||
orderA := base
|
||||
orderA.Forwards = []bindv1alpha1.BindZone{
|
||||
mkFwd("unkin.net", "198.18.200.6"), mkFwd("consul", "198.18.19.14"),
|
||||
mkFwd("k8s.syd1.au.unkin.net", "198.18.200.8"), mkFwd("13.18.198.in-addr.arpa", "198.18.200.6"),
|
||||
}
|
||||
orderB := base
|
||||
orderB.Forwards = []bindv1alpha1.BindZone{
|
||||
mkFwd("13.18.198.in-addr.arpa", "198.18.200.6"), mkFwd("k8s.syd1.au.unkin.net", "198.18.200.8"),
|
||||
mkFwd("consul", "198.18.19.14"), mkFwd("unkin.net", "198.18.200.6"),
|
||||
}
|
||||
pa, _ := RenderNamedConf(orderA)
|
||||
pb, _ := RenderNamedConf(orderB)
|
||||
if pa != pb {
|
||||
t.Fatalf("render must be independent of forward-zone input order:\n--- A ---\n%s\n--- B ---\n%s", pa, pb)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user