Skip to content

Commit cbf3832

Browse files
committed
Add basic probe checks
Start Probez
1 parent bcd06b8 commit cbf3832

File tree

5 files changed

+146
-0
lines changed

5 files changed

+146
-0
lines changed

cmd/nginx-k8s-edge-controller/main.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import (
99
"fmt"
1010
"github.com/nginxinc/kubernetes-nginx-ingress/internal/config"
1111
"github.com/nginxinc/kubernetes-nginx-ingress/internal/observation"
12+
"github.com/nginxinc/kubernetes-nginx-ingress/internal/probation"
1213
"github.com/nginxinc/kubernetes-nginx-ingress/internal/synchronization"
1314
"github.com/sirupsen/logrus"
1415
"k8s.io/client-go/kubernetes"
@@ -68,6 +69,9 @@ func run() error {
6869
go handler.Run(ctx.Done())
6970
go synchronizer.Run(ctx.Done())
7071

72+
probeServer := probation.NewHealthServer()
73+
probeServer.Start()
74+
7175
err = watcher.Watch()
7276
if err != nil {
7377
return fmt.Errorf(`error occurred watching for events: %w`, err)

deployment/nkl-deployment.yaml

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,4 +21,20 @@ spec:
2121
value: "http://10.1.1.4:9000/api"
2222
image: ciroque/nginx-k8s-edge-controller:latest
2323
imagePullPolicy: Always
24+
ports:
25+
- name: http
26+
containerPort: 51031
27+
protocol: TCP
28+
livenessProbe:
29+
httpGet:
30+
path: /livez
31+
port: http
32+
initialDelaySeconds: 5
33+
periodSeconds: 2
34+
readinessProbe:
35+
httpGet:
36+
path: /readyz
37+
port: http
38+
initialDelaySeconds: 5
39+
periodSeconds: 2
2440
serviceAccountName: nginx-k8s-edge-controller

internal/probation/check.go

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
// Copyright 2023 f5 Inc. All rights reserved.
2+
// Use of this source code is governed by the Apache
3+
// license that can be found in the LICENSE file.
4+
5+
package probation
6+
7+
type Check interface {
8+
Check() bool
9+
}
10+
11+
type LiveCheck struct {
12+
}
13+
14+
type ReadyCheck struct {
15+
}
16+
17+
type StartupCheck struct {
18+
}
19+
20+
func (l *LiveCheck) Check() bool {
21+
return true
22+
}
23+
24+
func (r *ReadyCheck) Check() bool {
25+
return true
26+
}
27+
28+
func (s *StartupCheck) Check() bool {
29+
return true
30+
}

internal/probation/doc.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
// Copyright 2023 f5 Inc. All rights reserved.
2+
// Use of this source code is governed by the Apache
3+
// license that can be found in the LICENSE file.
4+
5+
/*
6+
Package probation includes support for Kubernetes health and wellness checks.
7+
*/
8+
9+
package probation

internal/probation/server.go

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
// Copyright 2023 f5 Inc. All rights reserved.
2+
// Use of this source code is governed by the Apache
3+
// license that can be found in the LICENSE file.
4+
5+
package probation
6+
7+
import (
8+
"fmt"
9+
"github.com/sirupsen/logrus"
10+
"net/http"
11+
)
12+
13+
const (
14+
Ok = "OK"
15+
ServiceNotAvailable = "Service Not Available"
16+
ListenPort = 51031
17+
)
18+
19+
type HealthServer struct {
20+
httpServer *http.Server
21+
LiveCheck LiveCheck
22+
ReadyCheck ReadyCheck
23+
StartupCheck StartupCheck
24+
}
25+
26+
func NewHealthServer() *HealthServer {
27+
return &HealthServer{
28+
LiveCheck: LiveCheck{},
29+
ReadyCheck: ReadyCheck{},
30+
StartupCheck: StartupCheck{},
31+
}
32+
}
33+
34+
func (hs *HealthServer) Start() {
35+
logrus.Debugf("Starting probe listener on port %d", ListenPort)
36+
37+
address := fmt.Sprintf(":%d", ListenPort)
38+
39+
mux := http.NewServeMux()
40+
mux.HandleFunc("/livez", hs.HandleLive)
41+
mux.HandleFunc("/readyz", hs.HandleReady)
42+
mux.HandleFunc("/startupz", hs.HandleStartup)
43+
hs.httpServer = &http.Server{Addr: address, Handler: mux}
44+
45+
go func() {
46+
if err := hs.httpServer.ListenAndServe(); err != nil {
47+
logrus.Errorf("unable to start probe listener on %s: %v", hs.httpServer.Addr, err)
48+
}
49+
}()
50+
51+
logrus.Info("Started probe listener on", hs.httpServer.Addr)
52+
}
53+
54+
func (hs *HealthServer) Stop() {
55+
if err := hs.httpServer.Close(); err != nil {
56+
logrus.Errorf("unable to stop probe listener on %s: %v", hs.httpServer.Addr, err)
57+
}
58+
}
59+
60+
func (hs *HealthServer) HandleLive(writer http.ResponseWriter, request *http.Request) {
61+
handleProbe(writer, request, &hs.LiveCheck)
62+
}
63+
64+
func (hs *HealthServer) HandleReady(writer http.ResponseWriter, request *http.Request) {
65+
handleProbe(writer, request, &hs.ReadyCheck)
66+
}
67+
68+
func (hs *HealthServer) HandleStartup(writer http.ResponseWriter, request *http.Request) {
69+
handleProbe(writer, request, &hs.StartupCheck)
70+
}
71+
72+
func handleProbe(writer http.ResponseWriter, _ *http.Request, check Check) {
73+
if check.Check() {
74+
writer.WriteHeader(http.StatusOK)
75+
76+
if _, err := fmt.Fprint(writer, Ok); err != nil {
77+
logrus.Error(err)
78+
}
79+
80+
} else {
81+
writer.WriteHeader(http.StatusServiceUnavailable)
82+
83+
if _, err := fmt.Fprint(writer, ServiceNotAvailable); err != nil {
84+
logrus.Error(err)
85+
}
86+
}
87+
}

0 commit comments

Comments
 (0)