mirror of
https://github.com/traefik/mesh.git
synced 2026-05-02 18:32:32 +00:00
105 lines
2.8 KiB
Go
105 lines
2.8 KiB
Go
package api
|
|
|
|
import (
|
|
"encoding/json"
|
|
"fmt"
|
|
"net/http"
|
|
"time"
|
|
|
|
"github.com/gorilla/mux"
|
|
"github.com/sirupsen/logrus"
|
|
"github.com/traefik/mesh/v2/pkg/provider"
|
|
"github.com/traefik/mesh/v2/pkg/safe"
|
|
"github.com/traefik/mesh/v2/pkg/topology"
|
|
"github.com/traefik/traefik/v2/pkg/config/dynamic"
|
|
)
|
|
|
|
// API is an implementation of an api.
|
|
type API struct {
|
|
http.Server
|
|
|
|
readiness *safe.Safe
|
|
configuration *safe.Safe
|
|
topology *safe.Safe
|
|
|
|
namespace string
|
|
logger logrus.FieldLogger
|
|
}
|
|
|
|
// NewAPI creates a new api.
|
|
func NewAPI(logger logrus.FieldLogger, port int32, host, namespace string) *API {
|
|
router := mux.NewRouter()
|
|
|
|
api := &API{
|
|
Server: http.Server{
|
|
Addr: fmt.Sprintf("%s:%d", host, port),
|
|
ReadTimeout: 5 * time.Second,
|
|
WriteTimeout: 5 * time.Second,
|
|
Handler: router,
|
|
},
|
|
configuration: safe.New(provider.NewDefaultDynamicConfig()),
|
|
topology: safe.New(topology.NewTopology()),
|
|
readiness: safe.New(false),
|
|
namespace: namespace,
|
|
logger: logger,
|
|
}
|
|
|
|
router.HandleFunc("/api/configuration", api.getConfiguration)
|
|
router.HandleFunc("/api/topology", api.getTopology)
|
|
router.HandleFunc("/api/ready", api.getReadiness)
|
|
|
|
return api
|
|
}
|
|
|
|
// SetReadiness sets the readiness flag in the API.
|
|
func (a *API) SetReadiness(isReady bool) {
|
|
a.readiness.Set(isReady)
|
|
a.logger.Debugf("API readiness: %t", isReady)
|
|
}
|
|
|
|
// SetConfiguration sets the current dynamic configuration.
|
|
func (a *API) SetConfiguration(cfg *dynamic.Configuration) {
|
|
a.configuration.Set(cfg)
|
|
}
|
|
|
|
// SetTopology sets the current topology.
|
|
func (a *API) SetTopology(topo *topology.Topology) {
|
|
a.topology.Set(topo)
|
|
}
|
|
|
|
// getConfiguration returns the current configuration.
|
|
func (a *API) getConfiguration(w http.ResponseWriter, _ *http.Request) {
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
|
if err := json.NewEncoder(w).Encode(a.configuration.Get()); err != nil {
|
|
a.logger.Errorf("Unable to serialize configuration: %v", err)
|
|
http.Error(w, "", http.StatusInternalServerError)
|
|
}
|
|
}
|
|
|
|
// getTopology returns the current topology.
|
|
func (a *API) getTopology(w http.ResponseWriter, _ *http.Request) {
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
|
if err := json.NewEncoder(w).Encode(a.topology.Get()); err != nil {
|
|
a.logger.Errorf("Unable to serialize topology: %v", err)
|
|
http.Error(w, "", http.StatusInternalServerError)
|
|
}
|
|
}
|
|
|
|
// getReadiness returns the current readiness value, and sets the status code to 500 if not ready.
|
|
func (a *API) getReadiness(w http.ResponseWriter, _ *http.Request) {
|
|
isReady, _ := a.readiness.Get().(bool)
|
|
if !isReady {
|
|
http.Error(w, "", http.StatusInternalServerError)
|
|
return
|
|
}
|
|
|
|
w.Header().Set("Content-Type", "application/json")
|
|
|
|
if err := json.NewEncoder(w).Encode(isReady); err != nil {
|
|
a.logger.Errorf("Unable to serialize readiness: %v", err)
|
|
http.Error(w, "", http.StatusInternalServerError)
|
|
}
|
|
}
|