Add support for a default backend service

This commit is contained in:
Geoff Bourne
2019-04-19 20:27:14 -05:00
parent d76e5442da
commit 44a67dd359
5 changed files with 197 additions and 33 deletions
+42 -19
View File
@@ -12,6 +12,11 @@ import (
"net"
)
const (
AnnotationExternalServerName = "mc-router.itzg.me/externalServerName"
AnnotationDefaultServer = "mc-router.itzg.me/defaultServer"
)
type IK8sWatcher interface {
StartWithConfig(kubeConfigFile string) error
StartInCluster() error
@@ -65,7 +70,11 @@ func (w *k8sWatcherImpl) startWithLoadedConfig(config *rest.Config) error {
if routableService != nil {
logrus.WithField("routableService", routableService).Debug("ADD")
Routes.CreateMapping(routableService.externalServiceName, routableService.containerEndpoint)
if routableService.externalServiceName != "" {
Routes.CreateMapping(routableService.externalServiceName, routableService.containerEndpoint)
} else {
Routes.SetDefaultRoute(routableService.containerEndpoint)
}
}
},
DeleteFunc: func(obj interface{}) {
@@ -73,7 +82,11 @@ func (w *k8sWatcherImpl) startWithLoadedConfig(config *rest.Config) error {
if routableService != nil {
logrus.WithField("routableService", routableService).Debug("DELETE")
Routes.DeleteMapping(routableService.externalServiceName)
if routableService.externalServiceName != "" {
Routes.DeleteMapping(routableService.externalServiceName)
} else {
Routes.SetDefaultRoute("")
}
}
},
UpdateFunc: func(oldObj, newObj interface{}) {
@@ -85,8 +98,12 @@ func (w *k8sWatcherImpl) startWithLoadedConfig(config *rest.Config) error {
"new": newRoutableService,
}).Debug("UPDATE")
Routes.DeleteMapping(oldRoutableService.externalServiceName)
Routes.CreateMapping(newRoutableService.externalServiceName, newRoutableService.containerEndpoint)
if oldRoutableService.externalServiceName != "" && newRoutableService.externalServiceName != "" {
Routes.DeleteMapping(oldRoutableService.externalServiceName)
Routes.CreateMapping(newRoutableService.externalServiceName, newRoutableService.containerEndpoint)
} else {
Routes.SetDefaultRoute(newRoutableService.containerEndpoint)
}
}
},
},
@@ -116,22 +133,28 @@ func extractRoutableService(obj interface{}) *routableService {
return nil
}
if externalServiceName, exists := service.Annotations["mc-router.itzg.me/externalServerName"]; exists {
clusterIp := service.Spec.ClusterIP
port := "25565"
for _, p := range service.Spec.Ports {
if p.Port == 25565 {
if p.TargetPort.String() != "" {
port = p.TargetPort.String()
}
}
}
rs := &routableService{
externalServiceName: externalServiceName,
containerEndpoint: net.JoinHostPort(clusterIp, port),
}
return rs
if externalServiceName, exists := service.Annotations[AnnotationExternalServerName]; exists {
return buildDetails(service, externalServiceName)
} else if _, exists := service.Annotations[AnnotationDefaultServer]; exists {
return buildDetails(service, "")
}
return nil
}
func buildDetails(service *v1.Service, externalServiceName string) *routableService {
clusterIp := service.Spec.ClusterIP
port := "25565"
for _, p := range service.Spec.Ports {
if p.Port == 25565 {
if p.TargetPort.String() != "" {
port = p.TargetPort.String()
}
}
}
rs := &routableService{
externalServiceName: externalServiceName,
containerEndpoint: net.JoinHostPort(clusterIp, port),
}
return rs
}
+46 -9
View File
@@ -1,11 +1,11 @@
package server
import (
"sync"
"net/http"
"encoding/json"
"github.com/sirupsen/logrus"
"github.com/gorilla/mux"
"github.com/sirupsen/logrus"
"net/http"
"sync"
)
func init() {
@@ -15,6 +15,9 @@ func init() {
apiRoutes.Path("/routes").Methods("POST").
Headers("Content-Type", "application/json").
HandlerFunc(routesCreateHandler)
apiRoutes.Path("/defaultRoute").Methods("POST").
Headers("Content-Type", "application/json").
HandlerFunc(routesSetDefault)
apiRoutes.Path("/routes/{serverAddress}").Methods("DELETE").HandlerFunc(routesDeleteHandler)
}
@@ -43,7 +46,7 @@ func routesDeleteHandler(writer http.ResponseWriter, request *http.Request) {
func routesCreateHandler(writer http.ResponseWriter, request *http.Request) {
var definition = struct {
ServerAddress string
Backend string
Backend string
}{}
defer request.Body.Close()
@@ -60,6 +63,25 @@ func routesCreateHandler(writer http.ResponseWriter, request *http.Request) {
writer.WriteHeader(http.StatusCreated)
}
func routesSetDefault(writer http.ResponseWriter, request *http.Request) {
var body = struct {
Backend string
}{}
defer request.Body.Close()
decoder := json.NewDecoder(request.Body)
err := decoder.Decode(&body)
if err != nil {
logrus.WithError(err).Error("Unable to parse request")
writer.WriteHeader(http.StatusBadRequest)
return
}
Routes.SetDefaultRoute(body.Backend)
writer.WriteHeader(http.StatusOK)
}
type IRoutes interface {
RegisterAll(mappings map[string]string)
// FindBackendForServerAddress returns the host:port for the external server address, if registered.
@@ -68,6 +90,7 @@ type IRoutes interface {
GetMappings() map[string]string
DeleteMapping(serverAddress string) bool
CreateMapping(serverAddress string, backend string)
SetDefaultRoute(backend string)
}
var Routes IRoutes = &routesImpl{}
@@ -81,7 +104,16 @@ func (r *routesImpl) RegisterAll(mappings map[string]string) {
type routesImpl struct {
sync.RWMutex
mappings map[string]string
mappings map[string]string
defaultRoute string
}
func (r *routesImpl) SetDefaultRoute(backend string) {
r.defaultRoute = backend
logrus.WithFields(logrus.Fields{
"backend": backend,
}).Info("Using default route")
}
func (r *routesImpl) FindBackendForServerAddress(serverAddress string) string {
@@ -89,9 +121,14 @@ func (r *routesImpl) FindBackendForServerAddress(serverAddress string) string {
defer r.RUnlock()
if r.mappings == nil {
return ""
return r.defaultRoute
} else {
return r.mappings[serverAddress]
if route, exists := r.mappings[serverAddress]; exists {
return route
} else {
return r.defaultRoute
}
}
}
@@ -125,7 +162,7 @@ func (r *routesImpl) CreateMapping(serverAddress string, backend string) {
logrus.WithFields(logrus.Fields{
"serverAddress": serverAddress,
"backend": backend,
"backend": backend,
}).Info("Creating route")
r.mappings[serverAddress] = backend
}
}