caddy/middleware/headers.go
2015-01-21 12:09:49 -07:00

92 lines
1.6 KiB
Go

package middleware
import "net/http"
// Headers is middleware that adds headers to the responses
// for requests matching a certain path.
func Headers(p parser) Middleware {
type (
// Header represents a single HTTP header, simply a name and value.
header struct {
Name string
Value string
}
// Headers groups a slice of HTTP headers by a URL pattern.
headers struct {
Url string
Headers []header
}
)
var rules []headers
for p.NextLine() {
var head headers
var isNewPattern bool
if !p.NextArg() {
return p.ArgErr()
}
pattern := p.Val()
// See if we already have a definition for this URL pattern...
for _, h := range rules {
if h.Url == pattern {
head = h
break
}
}
// ...otherwise, this is a new pattern
if head.Url == "" {
head.Url = pattern
isNewPattern = true
}
for p.NextBlock() {
h := header{Name: p.Val()}
if p.NextArg() {
h.Value = p.Val()
}
head.Headers = append(head.Headers, h)
}
if p.NextArg() {
h := header{Name: p.Val()}
h.Value = p.Val()
if p.NextArg() {
h.Value = p.Val()
}
head.Headers = append(head.Headers, h)
}
if isNewPattern {
rules = append(rules, head)
} else {
for i := 0; i < len(rules); i++ {
if rules[i].Url == pattern {
rules[i] = head
break
}
}
}
}
return func(next http.HandlerFunc) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
for _, rule := range rules {
if Path(r.URL.Path).Matches(rule.Url) {
for _, header := range rule.Headers {
w.Header().Set(header.Name, header.Value)
}
}
}
next(w, r)
}
}
}