Skip to content

Commit

Permalink
Use github.com/heptio/healthcheck
Browse files Browse the repository at this point in the history
Rather than a handrolled solution, this commit uses heptio's healthcheck
library. Future consumers of the health check handler need only to
register liveness or readiness probes.

Update install.yaml to use /live for liveness check.

Also, inline health handler function for consistent style.
  • Loading branch information
enocom committed Feb 27, 2018
1 parent 2a3f827 commit 6f9dc38
Show file tree
Hide file tree
Showing 317 changed files with 48,122 additions and 39 deletions.
51 changes: 51 additions & 0 deletions Gopkg.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions Gopkg.toml
Original file line number Diff line number Diff line change
Expand Up @@ -47,3 +47,7 @@
[[constraint]]
branch = "master"
name = "github.com/mattbaird/jsonpatch"

[[constraint]]
branch = "master"
name = "github.com/heptiolabs/healthcheck"
4 changes: 2 additions & 2 deletions build/install.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ spec:
value: "8000"
livenessProbe:
httpGet:
path: /healthz
path: /live
port: 8080
initialDelaySeconds: 3
periodSeconds: 3
Expand Down Expand Up @@ -288,4 +288,4 @@ subjects:
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: agones-controller
name: agones-controller
25 changes: 23 additions & 2 deletions cmd/controller/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
package main

import (
"net/http"
"os"
"path/filepath"
"strings"
Expand All @@ -28,6 +29,8 @@ import (
"agones.dev/agones/pkg/util/runtime"
"agones.dev/agones/pkg/util/signals"
"agones.dev/agones/pkg/util/webhooks"
"github.com/heptiolabs/healthcheck"
"github.com/pkg/errors"
"github.com/spf13/pflag"
"github.com/spf13/viper"
extclientset "k8s.io/apiextensions-apiserver/pkg/client/clientset/clientset"
Expand Down Expand Up @@ -120,11 +123,12 @@ func main() {
logger.WithError(err).Fatal("Could not create the agones api clientset")
}

health := healthcheck.NewHandler()
wh := webhooks.NewWebHook(certFile, keyFile)
agonesInformerFactory := externalversions.NewSharedInformerFactory(agonesClient, 30*time.Second)
kubeInformationFactory := informers.NewSharedInformerFactory(kubeClient, 30*time.Second)

wh := webhooks.NewWebHook(certFile, keyFile)
c := gameservers.NewController(wh, minPort, maxPort, sidecarImage, alwaysPullSidecar, kubeClient, kubeInformationFactory, extClient, agonesClient, agonesInformerFactory)
c := gameservers.NewController(wh, health, minPort, maxPort, sidecarImage, alwaysPullSidecar, kubeClient, kubeInformationFactory, extClient, agonesClient, agonesInformerFactory)

stop := signals.NewStopChannel()

Expand All @@ -136,6 +140,23 @@ func main() {
logger.WithError(err).Fatal("could not run webhook server")
}
}()
go func() {
logger.Info("Starting health check...")
srv := &http.Server{
Addr: ":8080",
Handler: health,
}
defer srv.Close() // nolint: errcheck

if err := srv.ListenAndServe(); err != nil {
if err == http.ErrServerClosed {
logger.WithError(err).Info("health check: http server closed")
} else {
err := errors.Wrap(err, "Could not listen on :8080")
runtime.HandleError(logger.WithError(err), err)
}
}
}()

err = c.Run(2, stop)
if err != nil {
Expand Down
31 changes: 2 additions & 29 deletions pkg/gameservers/controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ package gameservers
import (
"encoding/json"
"fmt"
"net/http"

"agones.dev/agones/pkg/apis/stable"
stablev1alpha1 "agones.dev/agones/pkg/apis/stable/v1alpha1"
Expand All @@ -29,6 +28,7 @@ import (
"agones.dev/agones/pkg/util/runtime"
"agones.dev/agones/pkg/util/webhooks"
"agones.dev/agones/pkg/util/workerqueue"
"github.com/heptiolabs/healthcheck"
"github.com/mattbaird/jsonpatch"
"github.com/pkg/errors"
"github.com/sirupsen/logrus"
Expand Down Expand Up @@ -68,13 +68,13 @@ type Controller struct {
portAllocator *PortAllocator
healthController *HealthController
workerqueue *workerqueue.WorkerQueue
server *http.Server
recorder record.EventRecorder
}

// NewController returns a new gameserver crd controller
func NewController(
wh *webhooks.WebHook,
health healthcheck.Handler,
minPort, maxPort int32,
sidecarImage string,
alwaysPullSidecarImage bool,
Expand Down Expand Up @@ -137,20 +137,6 @@ func NewController(
},
})

mux := http.NewServeMux()
mux.HandleFunc("/healthz", func(w http.ResponseWriter, r *http.Request) {
_, err := w.Write([]byte("ok"))
if err != nil {
c.logger.WithError(err).Error("could not send ok response on healthz")
w.WriteHeader(http.StatusInternalServerError)
}
})

c.server = &http.Server{
Addr: ":8080",
Handler: mux,
}

return c
}

Expand Down Expand Up @@ -217,19 +203,6 @@ func (c *Controller) creationHandler(review admv1beta1.AdmissionReview) (admv1be
// Run the GameServer controller. Will block until stop is closed.
// Runs threadiness number workers to process the rate limited queue
func (c *Controller) Run(threadiness int, stop <-chan struct{}) error {
c.logger.Info("Starting health check...")
go func() {
if err := c.server.ListenAndServe(); err != nil {
if err == http.ErrServerClosed {
c.logger.WithError(err).Info("health check: http server closed")
} else {
err := errors.Wrap(err, "Could not listen on :8080")
runtime.HandleError(c.logger.WithError(err), err)
}
}
}()
defer c.server.Close() // nolint: errcheck

err := crd.WaitForEstablishedCRD(c.crdGetter, "gameservers.stable.agones.dev", c.logger)
if err != nil {
return err
Expand Down
16 changes: 11 additions & 5 deletions pkg/gameservers/controller_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
"agones.dev/agones/pkg/apis/stable"
"agones.dev/agones/pkg/apis/stable/v1alpha1"
"agones.dev/agones/pkg/util/webhooks"
"github.com/heptiolabs/healthcheck"
"github.com/mattbaird/jsonpatch"
"github.com/sirupsen/logrus"
"github.com/stretchr/testify/assert"
Expand Down Expand Up @@ -185,24 +186,29 @@ func TestControllerWatchGameServers(t *testing.T) {
}

func TestControllerHealthCheck(t *testing.T) {
c, mocks := newFakeController()
mocks.extClient.AddReactor("get", "customresourcedefinitions", func(action k8stesting.Action) (bool, runtime.Object, error) {
m := newMocks()
m.extClient.AddReactor("get", "customresourcedefinitions", func(action k8stesting.Action) (bool, runtime.Object, error) {
return true, newEstablishedCRD(), nil
})
health := healthcheck.NewHandler()
c := NewController(webhooks.NewWebHook("", ""), health, 10, 20, "sidecar:dev", false,
m.kubeClient, m.kubeInformationFactory, m.extClient, m.agonesClient, m.agonesInformerFactory)

c.workerqueue.SyncHandler = func(name string) error {
return nil
}

stop, cancel := startInformers(mocks, c.gameServerSynced)
stop, cancel := startInformers(m, c.gameServerSynced)
defer cancel()

go http.ListenAndServe("localhost:9090", health)

go func() {
err := c.Run(1, stop)
assert.Nil(t, err, "Run should not error")
}()

testHTTPHealth(t, "http://localhost:8080/healthz", "ok", http.StatusOK)
testHTTPHealth(t, "http://localhost:9090/live", "{}\n", http.StatusOK)
}

func TestControllerCreationHandler(t *testing.T) {
Expand Down Expand Up @@ -820,7 +826,7 @@ func testWithNonZeroDeletionTimestamp(t *testing.T, state v1alpha1.State, f func
func newFakeController() (*Controller, mocks) {
m := newMocks()
wh := webhooks.NewWebHook("", "")
c := NewController(wh, 10, 20, "sidecar:dev", false,
c := NewController(wh, healthcheck.NewHandler(), 10, 20, "sidecar:dev", false,
m.kubeClient, m.kubeInformationFactory, m.extClient, m.agonesClient, m.agonesInformerFactory)
c.recorder = m.fakeRecorder
return c, m
Expand Down
2 changes: 1 addition & 1 deletion pkg/gameservers/helper_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -153,8 +153,8 @@ func testHTTPHealth(t *testing.T, url string, expectedResponse string, expectedS
defer resp.Body.Close()
body, err := ioutil.ReadAll(resp.Body)
assert.Nil(t, err, "(%s) read response error should be nil: %v", url, err)
assert.Equal(t, []byte(expectedResponse), body, "(%s) response body should be '%s'", url, expectedResponse)
assert.Equal(t, expectedStatus, resp.StatusCode, "url: %s", url)
assert.Equal(t, []byte(expectedResponse), body, "(%s) response body should be '%s'", url, expectedResponse)
}

return true, nil
Expand Down
2 changes: 2 additions & 0 deletions vendor/github.com/beorn7/perks/.gitignore

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

20 changes: 20 additions & 0 deletions vendor/github.com/beorn7/perks/LICENSE

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

31 changes: 31 additions & 0 deletions vendor/github.com/beorn7/perks/README.md

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

26 changes: 26 additions & 0 deletions vendor/github.com/beorn7/perks/histogram/bench_test.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 6f9dc38

Please sign in to comment.