This commit is contained in:
76
internal/httpapp/https_middleware.go
Normal file
76
internal/httpapp/https_middleware.go
Normal file
@@ -0,0 +1,76 @@
|
||||
package httpapp
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"strings"
|
||||
|
||||
"gitea.avt.data-center.id/othman.suseno/atlas/internal/errors"
|
||||
)
|
||||
|
||||
// httpsEnforcementMiddleware enforces HTTPS connections
|
||||
func (a *App) httpsEnforcementMiddleware(next http.Handler) http.Handler {
|
||||
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||
// Skip HTTPS enforcement for health checks and localhost
|
||||
if a.isPublicEndpoint(r.URL.Path) || isLocalhost(r) {
|
||||
next.ServeHTTP(w, r)
|
||||
return
|
||||
}
|
||||
|
||||
// If TLS is enabled, enforce HTTPS
|
||||
if a.tlsConfig != nil && a.tlsConfig.Enabled {
|
||||
// Check if request is already over HTTPS
|
||||
if r.TLS != nil {
|
||||
next.ServeHTTP(w, r)
|
||||
return
|
||||
}
|
||||
|
||||
// Check X-Forwarded-Proto header (for reverse proxies)
|
||||
if r.Header.Get("X-Forwarded-Proto") == "https" {
|
||||
next.ServeHTTP(w, r)
|
||||
return
|
||||
}
|
||||
|
||||
// Redirect HTTP to HTTPS
|
||||
httpsURL := "https://" + r.Host + r.URL.RequestURI()
|
||||
http.Redirect(w, r, httpsURL, http.StatusMovedPermanently)
|
||||
return
|
||||
}
|
||||
|
||||
next.ServeHTTP(w, r)
|
||||
})
|
||||
}
|
||||
|
||||
// isLocalhost checks if the request is from localhost
|
||||
func isLocalhost(r *http.Request) bool {
|
||||
host := r.Host
|
||||
if strings.Contains(host, ":") {
|
||||
host = strings.Split(host, ":")[0]
|
||||
}
|
||||
return host == "localhost" || host == "127.0.0.1" || host == "::1"
|
||||
}
|
||||
|
||||
// requireHTTPSMiddleware requires HTTPS for all requests (strict mode)
|
||||
func (a *App) requireHTTPSMiddleware(next http.Handler) http.Handler {
|
||||
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||
// Skip for health checks
|
||||
if a.isPublicEndpoint(r.URL.Path) {
|
||||
next.ServeHTTP(w, r)
|
||||
return
|
||||
}
|
||||
|
||||
// If TLS is enabled, require HTTPS
|
||||
if a.tlsConfig != nil && a.tlsConfig.Enabled {
|
||||
// Check if request is over HTTPS
|
||||
if r.TLS == nil && r.Header.Get("X-Forwarded-Proto") != "https" {
|
||||
writeError(w, errors.NewAPIError(
|
||||
errors.ErrCodeForbidden,
|
||||
"HTTPS required",
|
||||
http.StatusForbidden,
|
||||
).WithDetails("this endpoint requires HTTPS"))
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
next.ServeHTTP(w, r)
|
||||
})
|
||||
}
|
||||
Reference in New Issue
Block a user