package api import ( "crypto/subtle" "net/http" "strings" ) // bearerAuth is a bootstrap bearer-token gate against the configured admin // token. Milestone 1+: replace with DB-backed api_keys lookup (hash compare, // per-pod scoping). Until OPENMAIL_ADMIN_TOKEN is set, the API is closed. func (s *Server) bearerAuth(next http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { if s.cfg.AdminToken == "" { writeJSON(w, http.StatusServiceUnavailable, map[string]string{ "error": "auth_unconfigured", "message": "OPENMAIL_ADMIN_TOKEN not set; API is closed", }) return } const prefix = "Bearer " h := r.Header.Get("Authorization") if !strings.HasPrefix(h, prefix) || subtle.ConstantTimeCompare([]byte(strings.TrimPrefix(h, prefix)), []byte(s.cfg.AdminToken)) != 1 { writeJSON(w, http.StatusUnauthorized, map[string]string{"error": "unauthorized"}) return } next.ServeHTTP(w, r) }) }