1package terminal 2 3import ( 4 "net" 5 "net/http" 6 "regexp" 7 "strings" 8 9 log "github.com/sirupsen/logrus" 10) 11 12var scrubRegexp = regexp.MustCompile(`(?i)([\?&]((?:private|authenticity|rss)[\-_]token)|(?:X-AMZ-)?Signature)=[^&]*`) 13 14func fail500(w http.ResponseWriter, r *http.Request, err error) { 15 http.Error(w, "Internal server error", 500) 16 printError(r, err) 17} 18 19func printError(r *http.Request, err error) { 20 if r != nil { 21 log.WithFields(log.Fields{ 22 "method": r.Method, 23 "uri": scrubURLParams(r.RequestURI), 24 }).WithError(err).Error("error") 25 } else { 26 log.WithError(err).Error("unknown error") 27 } 28} 29 30func headerClone(h http.Header) http.Header { 31 h2 := make(http.Header, len(h)) 32 for k, vv := range h { 33 vv2 := make([]string, len(vv)) 34 copy(vv2, vv) 35 h2[k] = vv2 36 } 37 return h2 38} 39 40func setForwardedFor(newHeaders *http.Header, originalRequest *http.Request) { 41 if clientIP, _, err := net.SplitHostPort(originalRequest.RemoteAddr); err == nil { 42 var header string 43 44 // If we aren't the first proxy retain prior 45 // X-Forwarded-For information as a comma+space 46 // separated list and fold multiple headers into one. 47 if prior, ok := originalRequest.Header["X-Forwarded-For"]; ok { 48 header = strings.Join(prior, ", ") + ", " + clientIP 49 } else { 50 header = clientIP 51 } 52 newHeaders.Set("X-Forwarded-For", header) 53 } 54} 55 56// ScrubURLParams replaces the content of any sensitive query string parameters 57// in an URL with `[FILTERED]` 58func scrubURLParams(url string) string { 59 return scrubRegexp.ReplaceAllString(url, "$1=[FILTERED]") 60} 61