diff --git a/authenticate/handlers.go b/authenticate/handlers.go index 6175dce16..a22dfec2f 100644 --- a/authenticate/handlers.go +++ b/authenticate/handlers.go @@ -33,7 +33,6 @@ import ( "github.com/pomerium/pomerium/pkg/grpc/directory" "github.com/pomerium/pomerium/pkg/grpc/session" "github.com/pomerium/pomerium/pkg/grpc/user" - "github.com/pomerium/pomerium/ui" ) // Handler returns the authenticate service's handler chain. @@ -80,7 +79,7 @@ func (a *Authenticate) Mount(r *mux.Router) { } func (a *Authenticate) mountDashboard(r *mux.Router) { - sr := r.PathPrefix("/.pomerium").Subrouter() + sr := httputil.DashboardSubrouter(r) c := cors.New(cors.Options{ AllowOriginRequestFunc: func(r *http.Request, _ string) bool { state := a.state.Load() @@ -108,19 +107,6 @@ func (a *Authenticate) mountDashboard(r *mux.Router) { handlers.DeviceEnrolled(authenticateURL, a.state.Load().sharedKey).ServeHTTP(w, r) return nil })) - for _, fileName := range []string{ - "apple-touch-icon.png", - "favicon-16x16.png", - "favicon-32x32.png", - "favicon.ico", - "index.css", - "index.js", - } { - fileName := fileName - sr.Path("/" + fileName).Handler(httputil.HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { - return ui.ServeFile(w, r, fileName) - })) - } cr := sr.PathPrefix("/callback").Subrouter() cr.Use(func(h http.Handler) http.Handler { diff --git a/authorize/check_response_test.go b/authorize/check_response_test.go index bdc30533c..7fad6b05d 100644 --- a/authorize/check_response_test.go +++ b/authorize/check_response_test.go @@ -135,6 +135,7 @@ func TestAuthorize_deniedResponse(t *testing.T) { Code: envoy_type_v3.StatusCode(codes.InvalidArgument), }, Headers: []*envoy_config_core_v3.HeaderValueOption{ + mkHeader("Content-Type", "text/html; charset=UTF-8", false), mkHeader("X-Pomerium-Intercepted-Response", "true", false), }, Body: "Access Denied", diff --git a/internal/httputil/errors.go b/internal/httputil/errors.go index 8bf21beaf..408acac90 100644 --- a/internal/httputil/errors.go +++ b/internal/httputil/errors.go @@ -78,6 +78,7 @@ func (e *HTTPError) ErrorResponse(w http.ResponseWriter, r *http.Request) { m["debugUrl"] = response.DebugURL.String() } + w.Header().Set("Content-Type", "text/html; charset=UTF-8") w.WriteHeader(response.Status) if err := ui.ServePage(w, r, "Error", m); err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) diff --git a/internal/httputil/router.go b/internal/httputil/router.go index 982a11f66..1dec755fd 100644 --- a/internal/httputil/router.go +++ b/internal/httputil/router.go @@ -4,8 +4,9 @@ import ( "net/http" "github.com/gorilla/mux" - "github.com/pomerium/csrf" + + "github.com/pomerium/pomerium/ui" ) // NewRouter returns a new router instance. @@ -21,3 +22,22 @@ func CSRFFailureHandler(w http.ResponseWriter, r *http.Request) error { } return nil } + +// DashboardSubrouter returns the .pomerium sub router. +func DashboardSubrouter(parent *mux.Router) *mux.Router { + r := parent.PathPrefix("/.pomerium").Subrouter() + for _, fileName := range []string{ + "apple-touch-icon.png", + "favicon-16x16.png", + "favicon-32x32.png", + "favicon.ico", + "index.css", + "index.js", + } { + fileName := fileName + r.Path("/" + fileName).Handler(HandlerFunc(func(w http.ResponseWriter, r *http.Request) error { + return ui.ServeFile(w, r, fileName) + })) + } + return r +} diff --git a/proxy/handlers.go b/proxy/handlers.go index 6b9413fd8..e22980887 100644 --- a/proxy/handlers.go +++ b/proxy/handlers.go @@ -18,7 +18,7 @@ import ( // registerDashboardHandlers returns the proxy service's ServeMux func (p *Proxy) registerDashboardHandlers(r *mux.Router) *mux.Router { - h := r.PathPrefix(dashboardPath).Subrouter() + h := httputil.DashboardSubrouter(r) h.Use(middleware.SetHeaders(httputil.HeadersContentSecurityPolicy)) // special pomerium endpoints for users to view their session