in dash.go [44:103]
func (d *Dash) Handler(prefix string) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
// create a timeout on the proxy request
ctx, cancel := context.WithTimeout(r.Context(), d.Config.ProxyTimeout)
defer cancel()
// build the object name
objName := strings.TrimPrefix(r.URL.Path, prefix)
if objName == "" || strings.HasSuffix(objName, "/") {
objName += "index.html"
}
if d.Prefix != "" {
objName = d.Prefix + "/" + objName
}
// get the object
gcsResp, err := d.getObject(ctx, r.Header, r.Method, objName)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
if gcsResp.StatusCode == http.StatusNotFound {
if d.SPA && objName != (d.Prefix+"/index.html") {
objName = "index.html"
if d.Prefix != "" {
objName = d.Prefix + "/" + objName
}
gcsResp.Body.Close()
gcsResp, err = d.getObject(ctx, r.Header, r.Method, objName)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
}
}
defer gcsResp.Body.Close()
// add dashboard name, bucket, and object to log
hlog.FromRequest(r).Info().
Str("dashboard", d.Name).
Str("bucket", d.Bucket).
Str("object", objName).
Msg("")
// copy GCS response headers and body to our response
for name, values := range gcsResp.Header {
for _, value := range values {
w.Header().Add(name, value)
}
}
w.WriteHeader(gcsResp.StatusCode)
if _, err = io.Copy(w, gcsResp.Body); err != nil {
http.Error(w, "500 Internal Server Error", http.StatusInternalServerError)
}
}
}