home/internal/middleware/header.go

68 lines
1.3 KiB
Go

package middleware
import (
"net/http"
"source.toby3d.me/toby3d/home/internal/domain"
"source.toby3d.me/toby3d/home/internal/server"
"source.toby3d.me/toby3d/home/internal/site"
"source.toby3d.me/toby3d/home/internal/urlutil"
)
type HeaderConfig struct {
Skipper Skipper
Siter site.UseCase
Serverer server.UseCase
}
func Header(config HeaderConfig) Interceptor {
if config.Skipper == nil {
config.Skipper = DefaultSkipper
}
if config.Siter == nil {
panic("middleware: header: Siter is nil")
}
if config.Serverer == nil {
panic("middleware: header: Serverer is nil")
}
return func(w http.ResponseWriter, r *http.Request, next http.HandlerFunc) {
if config.Skipper(r) {
next(w, r)
return
}
lang, path := domain.LanguageUnd, r.URL.Path
if head, tail := urlutil.ShiftPath(r.URL.Path); head != "" {
if lang = domain.NewLanguage(head); lang != domain.LanguageUnd {
path = tail
}
}
site, err := config.Siter.Do(r.Context(), lang)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
server, err := config.Serverer.Do(r.Context(), *site)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
for _, header := range server.Headers.Match(path) {
for k, v := range header.Values {
w.Header().Add(k, v)
}
}
next(w, r)
}
}