add "mox dkim sign", useful for testing signatures

for issue #15
This commit is contained in:
Mechiel Lukkien 2023-03-07 21:59:55 +01:00
parent 39a097a5d4
commit a9ef0f2aea
No known key found for this signature in database
2 changed files with 57 additions and 0 deletions

11
doc.go
View file

@ -50,6 +50,7 @@ low-maintenance self-hosted email.
mox dkim lookup selector domain mox dkim lookup selector domain
mox dkim txt <$selector._domainkey.$domain.key.pkcs8.pem mox dkim txt <$selector._domainkey.$domain.key.pkcs8.pem
mox dkim verify message mox dkim verify message
mox dkim sign message
mox dmarc lookup domain mox dmarc lookup domain
mox dmarc parsereportmsg message ... mox dmarc parsereportmsg message ...
mox dmarc verify remoteip mailfromaddress helodomain < message mox dmarc verify remoteip mailfromaddress helodomain < message
@ -503,6 +504,16 @@ that was passed.
usage: mox dkim verify message usage: mox dkim verify message
# mox dkim sign
Sign a message, adding DKIM-Signature headers based on the domain in the From header.
The message is parsed, the domain looked up in the configuration files, and
DKIM-Signature headers generated. The message is printed with the DKIM-Signature
headers prepended.
usage: mox dkim sign message
# mox dmarc lookup # mox dmarc lookup
Lookup dmarc policy for domain, a DNS TXT record at _dmarc.<domain>, validate and print it. Lookup dmarc policy for domain, a DNS TXT record at _dmarc.<domain>, validate and print it.

46
main.go
View file

@ -116,6 +116,7 @@ var commands = []struct {
{"dkim lookup", cmdDKIMLookup}, {"dkim lookup", cmdDKIMLookup},
{"dkim txt", cmdDKIMTXT}, {"dkim txt", cmdDKIMTXT},
{"dkim verify", cmdDKIMVerify}, {"dkim verify", cmdDKIMVerify},
{"dkim sign", cmdDKIMSign},
{"dmarc lookup", cmdDMARCLookup}, {"dmarc lookup", cmdDMARCLookup},
{"dmarc parsereportmsg", cmdDMARCParsereportmsg}, {"dmarc parsereportmsg", cmdDMARCParsereportmsg},
{"dmarc verify", cmdDMARCVerify}, {"dmarc verify", cmdDMARCVerify},
@ -1272,6 +1273,51 @@ that was passed.
} }
} }
func cmdDKIMSign(c *cmd) {
c.params = "message"
c.help = `Sign a message, adding DKIM-Signature headers based on the domain in the From header.
The message is parsed, the domain looked up in the configuration files, and
DKIM-Signature headers generated. The message is printed with the DKIM-Signature
headers prepended.
`
args := c.Parse()
if len(args) != 1 {
c.Usage()
}
msgf, err := os.Open(args[0])
xcheckf(err, "open message")
defer msgf.Close()
p, err := message.Parse(msgf)
xcheckf(err, "parsing message")
if len(p.Envelope.From) != 1 {
log.Fatalf("found %d from headers, need exactly 1", len(p.Envelope.From))
}
localpart := smtp.Localpart(p.Envelope.From[0].User)
dom, err := dns.ParseDomain(p.Envelope.From[0].Host)
xcheckf(err, "parsing domain in from header")
mustLoadConfig()
domConf, ok := mox.Conf.Domain(dom)
if !ok {
log.Fatalf("domain %s not configured", dom)
}
headers, err := dkim.Sign(context.Background(), localpart, dom, domConf.DKIM, false, msgf)
xcheckf(err, "signing message with dkim")
if headers == "" {
log.Fatalf("no DKIM configured for domain %s", dom)
}
_, err = fmt.Fprint(os.Stdout, headers)
xcheckf(err, "write headers")
_, err = io.Copy(os.Stdout, msgf)
xcheckf(err, "write message")
}
func cmdDKIMLookup(c *cmd) { func cmdDKIMLookup(c *cmd) {
c.params = "selector domain" c.params = "selector domain"
c.help = "Lookup and print the DKIM record for the selector at the domain." c.help = "Lookup and print the DKIM record for the selector at the domain."