mirror of
https://github.com/TwiN/gatus.git
synced 2024-11-07 08:34:15 +01:00
75 lines
2.2 KiB
Go
75 lines
2.2 KiB
Go
package security
|
|
|
|
import (
|
|
"net/http"
|
|
"strings"
|
|
|
|
"github.com/TwiN/g8"
|
|
"github.com/gorilla/mux"
|
|
)
|
|
|
|
const (
|
|
cookieNameState = "gatus_state"
|
|
cookieNameNonce = "gatus_nonce"
|
|
cookieNameSession = "gatus_session"
|
|
)
|
|
|
|
// Config is the security configuration for Gatus
|
|
type Config struct {
|
|
Basic *BasicConfig `yaml:"basic,omitempty"`
|
|
OIDC *OIDCConfig `yaml:"oidc,omitempty"`
|
|
}
|
|
|
|
// IsValid returns whether the security configuration is valid or not
|
|
func (c *Config) IsValid() bool {
|
|
return (c.Basic != nil && c.Basic.isValid()) || (c.OIDC != nil && c.OIDC.isValid())
|
|
}
|
|
|
|
// RegisterHandlers registers all handlers required based on the security configuration
|
|
func (c *Config) RegisterHandlers(router *mux.Router) error {
|
|
if c.OIDC != nil {
|
|
if err := c.OIDC.initialize(); err != nil {
|
|
return err
|
|
}
|
|
router.HandleFunc("/oidc/login", c.OIDC.loginHandler)
|
|
router.HandleFunc("/authorization-code/callback", c.OIDC.callbackHandler)
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func (c *Config) ApplySecurityMiddleware(api *mux.Router) {
|
|
if c.OIDC != nil {
|
|
// We're going to use g8 for session handling
|
|
clientProvider := g8.NewClientProvider(func(token string) *g8.Client {
|
|
if _, exists := sessions.Get(token); exists {
|
|
return g8.NewClient(token)
|
|
}
|
|
return nil
|
|
})
|
|
customTokenExtractorFunc := func(request *http.Request) string {
|
|
sessionCookie, err := request.Cookie(cookieNameSession)
|
|
if err != nil {
|
|
return ""
|
|
}
|
|
return sessionCookie.Value
|
|
}
|
|
// TODO: g8: Add a way to update cookie after? would need the writer
|
|
authorizationService := g8.NewAuthorizationService().WithClientProvider(clientProvider)
|
|
gate := g8.New().WithAuthorizationService(authorizationService).WithCustomTokenExtractor(customTokenExtractorFunc)
|
|
api.Use(gate.Protect)
|
|
} else if c.Basic != nil {
|
|
api.Use(func(handler http.Handler) http.Handler {
|
|
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
usernameEntered, passwordEntered, ok := r.BasicAuth()
|
|
if !ok || usernameEntered != c.Basic.Username || Sha512(passwordEntered) != strings.ToLower(c.Basic.PasswordSha512Hash) {
|
|
w.Header().Set("WWW-Authenticate", "Basic")
|
|
w.WriteHeader(http.StatusUnauthorized)
|
|
_, _ = w.Write([]byte("Unauthorized"))
|
|
return
|
|
}
|
|
handler.ServeHTTP(w, r)
|
|
})
|
|
})
|
|
}
|
|
}
|