Skip to content

Commit 9d7d164

Browse files
authored
fix: host readiness probe on ipv6 in addition to ipv4 (#3765)
Problem: the readiness probe endpoint is not available on IPv6. This is a problem on IPv6 only clusters when using IPv6 for the pod network. The gateway pod refuses to come up because the readyz condition never fulfills. Example: ``` Warning Unhealthy 88s (x160 over 26m) kubelet Readiness probe failed: Get "http://[fdd3:7046:2ad5:430a:39bb:bc6d:e254:a621]:8081/readyz": dial tcp [fdd3:7046:2ad5:430a:39bb:bc6d:e254:a621]:8081: connect: connection refused ``` Solution: host the readyz endpoint on IPv6 as well.
1 parent 4e366e8 commit 9d7d164

File tree

3 files changed

+60
-7
lines changed

3 files changed

+60
-7
lines changed

internal/controller/nginx/config/base_http_config.go

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,9 @@ var baseHTTPTemplate = gotemplate.Must(gotemplate.New("baseHttp").Parse(baseHTTP
1212

1313
type httpConfig struct {
1414
Includes []shared.Include
15-
HTTP2 bool
1615
NginxReadinessProbePort int32
16+
IPFamily shared.IPFamily
17+
HTTP2 bool
1718
}
1819

1920
func executeBaseHTTPConfig(conf dataplane.Configuration) []executeResult {
@@ -23,6 +24,7 @@ func executeBaseHTTPConfig(conf dataplane.Configuration) []executeResult {
2324
HTTP2: conf.BaseHTTPConfig.HTTP2,
2425
Includes: includes,
2526
NginxReadinessProbePort: conf.BaseHTTPConfig.NginxReadinessProbePort,
27+
IPFamily: getIPFamily(conf.BaseHTTPConfig),
2628
}
2729

2830
results := make([]executeResult, 0, len(includes)+1)

internal/controller/nginx/config/base_http_config_template.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,12 @@ map $request_uri $request_uri_path {
2626
2727
# NGINX health check server block.
2828
server {
29+
{{- if $.IPFamily.IPv4 }}
2930
listen {{ .NginxReadinessProbePort }};
31+
{{- end }}
32+
{{- if $.IPFamily.IPv6 }}
33+
listen [::]:{{ .NginxReadinessProbePort }};
34+
{{- end }}
3035
3136
location = /readyz {
3237
access_log off;

internal/controller/nginx/config/base_http_config_test.go

Lines changed: 52 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -117,30 +117,71 @@ func TestExecuteBaseHttp_NginxReadinessProbePort(t *testing.T) {
117117
},
118118
}
119119

120-
customConfig := dataplane.Configuration{
120+
customPortConfig := dataplane.Configuration{
121121
BaseHTTPConfig: dataplane.BaseHTTPConfig{
122122
NginxReadinessProbePort: 9090,
123123
},
124124
}
125125

126+
customIPv4Config := dataplane.Configuration{
127+
BaseHTTPConfig: dataplane.BaseHTTPConfig{
128+
NginxReadinessProbePort: dataplane.DefaultNginxReadinessProbePort,
129+
IPFamily: dataplane.IPv4,
130+
},
131+
}
132+
133+
customIPv6Config := dataplane.Configuration{
134+
BaseHTTPConfig: dataplane.BaseHTTPConfig{
135+
NginxReadinessProbePort: dataplane.DefaultNginxReadinessProbePort,
136+
IPFamily: dataplane.IPv6,
137+
},
138+
}
139+
126140
tests := []struct {
127-
name string
128-
expectedPort string
129-
expectedListen string
130-
conf dataplane.Configuration
141+
name string
142+
expectedPort string
143+
expectedListen string
144+
expectedNoListen string
145+
conf dataplane.Configuration
131146
}{
132147
{
133148
name: "default nginx readiness probe port",
134149
conf: defaultConfig,
135150
expectedPort: "8081",
136151
expectedListen: "listen 8081;",
137152
},
153+
{
154+
name: "default nginx readiness probe port on ipv6",
155+
conf: defaultConfig,
156+
expectedPort: "8081",
157+
expectedListen: "listen [::]:8081;",
158+
},
138159
{
139160
name: "custom nginx readiness probe 9090",
140-
conf: customConfig,
161+
conf: customPortConfig,
141162
expectedPort: "9090",
142163
expectedListen: "listen 9090;",
143164
},
165+
{
166+
name: "custom nginx readiness probe 9090 on ipv6",
167+
conf: customPortConfig,
168+
expectedPort: "9090",
169+
expectedListen: "listen [::]:9090;",
170+
},
171+
{
172+
name: "custom ipv4 nginx readiness probe does not have ipv6 listen",
173+
conf: customIPv4Config,
174+
expectedPort: "8081",
175+
expectedListen: "listen 8081;",
176+
expectedNoListen: "listen [::]:8081;",
177+
},
178+
{
179+
name: "custom ipv6 nginx readiness probe does not have ipv4 listen",
180+
conf: customIPv6Config,
181+
expectedPort: "8081",
182+
expectedListen: "listen [::]:8081;",
183+
expectedNoListen: "listen 8081;",
184+
},
144185
}
145186

146187
for _, test := range tests {
@@ -156,6 +197,11 @@ func TestExecuteBaseHttp_NginxReadinessProbePort(t *testing.T) {
156197
// check that the listen directive contains the expected port
157198
g.Expect(httpConfig).To(ContainSubstring(test.expectedListen))
158199

200+
// check that an additional listen directive is NOT set
201+
if test.expectedNoListen != "" {
202+
g.Expect(httpConfig).ToNot(ContainSubstring(test.expectedNoListen))
203+
}
204+
159205
// check that the health check server block is present
160206
g.Expect(httpConfig).To(ContainSubstring("server {"))
161207
g.Expect(httpConfig).To(ContainSubstring("access_log off;"))

0 commit comments

Comments
 (0)