mirror of
https://github.com/mjl-/mox.git
synced 2024-12-26 16:33:47 +03:00
ec967ef321
the stuttering was introduced to make the same type name declared in multiple packages, and used in the admin sherpa api, unique. with sherpadoc's new rename, we can make them unique when generating the api definition/docs, and the Go code can use nicer names.
75 lines
1.7 KiB
Go
75 lines
1.7 KiB
Go
package http
|
|
|
|
import (
|
|
"log/slog"
|
|
"net"
|
|
"net/http"
|
|
"strings"
|
|
"time"
|
|
|
|
"github.com/mjl-/mox/dns"
|
|
"github.com/mjl-/mox/mlog"
|
|
"github.com/mjl-/mox/mox-"
|
|
"github.com/mjl-/mox/mtasts"
|
|
)
|
|
|
|
func mtastsPolicyHandle(w http.ResponseWriter, r *http.Request) {
|
|
log := func() mlog.Log {
|
|
return pkglog.WithContext(r.Context())
|
|
}
|
|
|
|
host := strings.ToLower(r.Host)
|
|
if !strings.HasPrefix(host, "mta-sts.") {
|
|
http.NotFound(w, r)
|
|
return
|
|
}
|
|
host = strings.TrimPrefix(host, "mta-sts.")
|
|
nhost, _, err := net.SplitHostPort(host)
|
|
if err == nil {
|
|
// Only relevant for when host has a port.
|
|
host = nhost
|
|
}
|
|
domain, err := dns.ParseDomain(host)
|
|
if err != nil {
|
|
log().Errorx("mtasts policy request: bad domain", err, slog.String("host", host))
|
|
http.NotFound(w, r)
|
|
return
|
|
}
|
|
|
|
conf, _ := mox.Conf.Domain(domain)
|
|
sts := conf.MTASTS
|
|
if sts == nil {
|
|
http.NotFound(w, r)
|
|
return
|
|
}
|
|
|
|
var mxs []mtasts.MX
|
|
for _, s := range sts.MX {
|
|
var mx mtasts.MX
|
|
if strings.HasPrefix(s, "*.") {
|
|
mx.Wildcard = true
|
|
s = s[2:]
|
|
}
|
|
d, err := dns.ParseDomain(s)
|
|
if err != nil {
|
|
log().Errorx("bad domain in mtasts config", err, slog.String("domain", s))
|
|
http.Error(w, "500 - internal server error - invalid domain in configuration", http.StatusInternalServerError)
|
|
return
|
|
}
|
|
mx.Domain = d
|
|
mxs = append(mxs, mx)
|
|
}
|
|
if len(mxs) == 0 {
|
|
mxs = []mtasts.MX{{Domain: mox.Conf.Static.HostnameDomain}}
|
|
}
|
|
|
|
policy := mtasts.Policy{
|
|
Version: "STSv1",
|
|
Mode: sts.Mode,
|
|
MaxAgeSeconds: int(sts.MaxAge / time.Second),
|
|
MX: mxs,
|
|
}
|
|
w.Header().Set("Content-Type", "text/plain")
|
|
w.Header().Set("Cache-Control", "no-cache, max-age=0")
|
|
_, _ = w.Write([]byte(policy.String()))
|
|
}
|