diff --git a/handlers/handlers.go b/handlers/handlers.go new file mode 100644 index 0000000..d6bffde --- /dev/null +++ b/handlers/handlers.go @@ -0,0 +1,44 @@ +package handlers + +import ( + "fmt" + "net/http" +) + +// RootURL returns the root URL of the HTTP request. Optionally, a domain and a +// base path may be provided which will be used to construct the root URL if +// they are not empty. Otherwise the hostname will be determined from the +// request and the path will be empty. +func RootURL(r *http.Request, domain, path string) string { + host := r.Host + if len(domain) > 0 { + host = domain + } + + root := fmt.Sprintf("%s://%s", Scheme(r), host) + if len(path) > 0 { + root = fmt.Sprintf("%s/%s", root, path) + } + + return root +} + +// Scheme returns the underlying URL scheme of the original request. +func Scheme(r *http.Request) string { + if r.TLS != nil { + return "https" + } + if scheme := r.Header.Get("X-Forwarded-Proto"); scheme != "" { + return scheme + } + if scheme := r.Header.Get("X-Forwarded-Protocol"); scheme != "" { + return scheme + } + if ssl := r.Header.Get("X-Forwarded-Ssl"); ssl == "on" { + return "https" + } + if scheme := r.Header.Get("X-Url-Scheme"); scheme != "" { + return scheme + } + return "http" +} diff --git a/main.go b/main.go index 29c2cd5..c3d9051 100644 --- a/main.go +++ b/main.go @@ -25,6 +25,7 @@ import ( log "github.com/sirupsen/logrus" "github.com/spf13/cobra" + "github.com/consbio/mbtileserver/handlers" "github.com/consbio/mbtileserver/mbtiles" ) @@ -338,18 +339,10 @@ func getServiceOr404(c echo.Context) (string, error) { return id, nil } +// getRootURL is a convenience function to determine the root URL from the +// echo.Context. func getRootURL(c echo.Context) string { - host := c.Request().Host - if len(domain) > 0 { - host = domain - } - - root := fmt.Sprintf("%s://%s", c.Scheme(), host) - if len(path) > 0 { - root = fmt.Sprintf("%s/%s", root, path) - } - - return root + return handlers.RootURL(c.Request(), domain, path) } func ListServices(c echo.Context) error {