@@ -3,7 +3,11 @@ package controller
33import (
44 "testing"
55
6+ v1 "k8s.io/api/core/v1"
7+ metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
8+
69 "github.com/stretchr/testify/assert"
10+ "github.com/stretchr/testify/require"
711)
812
913func TestBuildCloudflaredCommand (t * testing.T ) {
@@ -100,3 +104,100 @@ func TestBuildCloudflaredCommand(t *testing.T) {
100104 }
101105}
102106
107+ func TestCloudflaredConnectDeploymentTemplating (t * testing.T ) {
108+ t .Run ("single replica has no anti-affinity" , func (t * testing.T ) {
109+ dep := cloudflaredConnectDeploymentTemplating ("quic" , "tok" , "ns" , 1 , nil )
110+
111+ assert .Equal (t , "controlled-cloudflared-connector" , dep .Name )
112+ assert .Equal (t , "ns" , dep .Namespace )
113+ assert .Equal (t , int32 (1 ), * dep .Spec .Replicas )
114+ assert .Nil (t , dep .Spec .Template .Spec .Affinity , "single replica should have no affinity" )
115+ })
116+
117+ t .Run ("multiple replicas have anti-affinity" , func (t * testing.T ) {
118+ dep := cloudflaredConnectDeploymentTemplating ("quic" , "tok" , "ns" , 3 , nil )
119+
120+ assert .Equal (t , int32 (3 ), * dep .Spec .Replicas )
121+ require .NotNil (t , dep .Spec .Template .Spec .Affinity )
122+ require .NotNil (t , dep .Spec .Template .Spec .Affinity .PodAntiAffinity )
123+
124+ terms := dep .Spec .Template .Spec .Affinity .PodAntiAffinity .RequiredDuringSchedulingIgnoredDuringExecution
125+ require .Len (t , terms , 1 )
126+ assert .Equal (t , "kubernetes.io/hostname" , terms [0 ].TopologyKey )
127+ assert .Equal (t , map [string ]string {"app" : "controlled-cloudflared-connector" }, terms [0 ].LabelSelector .MatchLabels )
128+ })
129+
130+ t .Run ("labels are consistent across object meta, selector, and template" , func (t * testing.T ) {
131+ dep := cloudflaredConnectDeploymentTemplating ("quic" , "tok" , "ns" , 2 , nil )
132+
133+ expectedLabels := map [string ]string {
134+ "app" : "controlled-cloudflared-connector" ,
135+ "strrl.dev/cloudflare-tunnel-ingress-controller" : "controlled-cloudflared-connector" ,
136+ }
137+ assert .Equal (t , expectedLabels , dep .Labels )
138+ assert .Equal (t , expectedLabels , dep .Spec .Selector .MatchLabels )
139+ assert .Equal (t , expectedLabels , dep .Spec .Template .Labels )
140+ })
141+
142+ t .Run ("container uses provided protocol and token" , func (t * testing.T ) {
143+ dep := cloudflaredConnectDeploymentTemplating ("http2" , "my-token" , "default" , 1 , []string {"--post-quantum" })
144+
145+ require .Len (t , dep .Spec .Template .Spec .Containers , 1 )
146+ c := dep .Spec .Template .Spec .Containers [0 ]
147+ assert .Equal (t , "controlled-cloudflared-connector" , c .Name )
148+ assert .Contains (t , c .Command , "http2" )
149+ assert .Contains (t , c .Command , "my-token" )
150+ assert .Contains (t , c .Command , "--post-quantum" )
151+ })
152+ }
153+
154+ func TestBuildPodAntiAffinity (t * testing.T ) {
155+ t .Run ("nil for single replica" , func (t * testing.T ) {
156+ assert .Nil (t , buildPodAntiAffinity ("app" , 1 ))
157+ })
158+
159+ t .Run ("nil for zero replicas" , func (t * testing.T ) {
160+ assert .Nil (t , buildPodAntiAffinity ("app" , 0 ))
161+ })
162+
163+ t .Run ("set for multiple replicas" , func (t * testing.T ) {
164+ aff := buildPodAntiAffinity ("my-app" , 3 )
165+ require .NotNil (t , aff )
166+ terms := aff .PodAntiAffinity .RequiredDuringSchedulingIgnoredDuringExecution
167+ require .Len (t , terms , 1 )
168+ assert .Equal (t , "kubernetes.io/hostname" , terms [0 ].TopologyKey )
169+ assert .Equal (t , map [string ]string {"app" : "my-app" }, terms [0 ].LabelSelector .MatchLabels )
170+ })
171+ }
172+
173+ func TestAffinityEqual (t * testing.T ) {
174+ aff1 := & v1.Affinity {
175+ PodAntiAffinity : & v1.PodAntiAffinity {
176+ RequiredDuringSchedulingIgnoredDuringExecution : []v1.PodAffinityTerm {
177+ {
178+ LabelSelector : & metav1.LabelSelector {
179+ MatchLabels : map [string ]string {"app" : "test" },
180+ },
181+ TopologyKey : "kubernetes.io/hostname" ,
182+ },
183+ },
184+ },
185+ }
186+ aff2 := & v1.Affinity {
187+ PodAntiAffinity : & v1.PodAntiAffinity {
188+ RequiredDuringSchedulingIgnoredDuringExecution : []v1.PodAffinityTerm {
189+ {
190+ LabelSelector : & metav1.LabelSelector {
191+ MatchLabels : map [string ]string {"app" : "test" },
192+ },
193+ TopologyKey : "kubernetes.io/hostname" ,
194+ },
195+ },
196+ },
197+ }
198+
199+ assert .True (t , affinityEqual (nil , nil ))
200+ assert .False (t , affinityEqual (aff1 , nil ))
201+ assert .False (t , affinityEqual (nil , aff1 ))
202+ assert .True (t , affinityEqual (aff1 , aff2 ))
203+ }
0 commit comments