This is the main dovel repository, it has the Go code to run dovel SMTP server.
Author: myr (myr@terminal.pink)
Date: Sat Sep 28 23:00:54 2024 -0300
Parent: 77ec29b
removed wkd part
diff --git a/backend.go b/backend.go
index e813f8a..074990c 100644
--- a/backend.go
+++ b/backend.go
@@ -2,9 +2,6 @@ package main
import (
"bytes"
- "crypto/rsa"
- "crypto/x509"
- "encoding/pem"
"fmt"
"io"
"log/slog"
@@ -17,10 +14,7 @@ import (
"time"
"github.com/emersion/go-mbox"
- "github.com/emersion/go-msgauth/dkim"
- wkd "github.com/emersion/go-openpgp-wkd"
"github.com/emersion/go-smtp"
- "golang.org/x/crypto/openpgp"
)
// A Session is returned after EHLO.
@@ -145,100 +139,32 @@ func (s *Session) Logout() error {
}
func (s *Session) Send(from string, tos []*mail.Address, raw io.Reader) error {
- email, err := mail.ReadMessage(raw)
+ content, err := io.ReadAll(raw)
if err != nil {
return err
}
- if email.Header.Get("message-id") == "" {
- email.Header["Message-ID"] = []string{
- fmt.Sprintf("%s%d", from, time.Now().Unix()),
- }
- }
- fromdom := strings.Split(from, "@")
- content, err := io.ReadAll(email.Body)
- if err != nil {
- return err
- }
for _, to := range tos {
slog.Debug("sending email", "to", to)
- body := content
// dns mx for email
addr := strings.Split(to.Address, "@")
mxs, err := net.LookupMX(addr[1])
if err != nil {
+ slog.Error("mx lookup", "address", addr[1])
return err
}
if len(mxs) == 0 {
+ slog.Error("mx lookup", "lenght", 0)
return err
}
- slog.Debug("checking wkd key")
- key, _ := wkd.Discover(to.Address)
- if key != nil {
- slog.Info("found WKD key", "address", to.Address)
- enc := bytes.Buffer{}
- c, err := openpgp.Encrypt(&enc, key, nil, nil, nil)
- if err != nil {
- return err
- }
- c.Write(content)
- c.Close()
- email.Header["Content-Type"] = []string{"application/pgp-encrypted"}
- body = enc.Bytes()
- slog.Debug("message encrypted", "content", body)
- }
-
- // write email headers into payload
- var headers string
- for k, v := range email.Header {
- headers += fmt.Sprintf(
- "%s: %s\r\n",
- k, strings.Join(v, ", "),
- )
- }
- headers += "\r\n"
- body = append([]byte(headers), body...)
-
- // dkim
- slog.Debug("dkim check")
- res := bytes.Buffer{}
- if keyPath := s.user.PrivateKey; keyPath != "" {
- slog.Info("user has dkim key")
-
- keyData, err := os.ReadFile(keyPath)
- if err != nil {
- return err
- }
- block, _ := pem.Decode(keyData)
- privateKey, err := x509.ParsePKCS8PrivateKey(block.Bytes)
- if err != nil {
- return err
- }
- options := &dkim.SignOptions{
- Domain: fromdom[1],
- Selector: "dkim",
- Signer: privateKey.(*rsa.PrivateKey),
- }
-
- err = dkim.Sign(&res, bytes.NewReader(body), options)
- if err != nil {
- slog.Error("failed to sign body", "err", err)
- }
- slog.Debug("signed")
- } else {
- slog.Info("no dkim key")
- io.Copy(&res, bytes.NewReader(body))
- }
-
addrs := make([]string, len(tos))
for i, to := range tos {
addrs[i] = to.Address
}
server := mxs[0].Host + ":smtp"
- content = res.Bytes()
slog.Info("sending", "host", server, "from", from, "to", tos)
slog.Debug("message", "data", content)
err = smtp.SendMail(
diff --git a/model.go b/model.go
index 7a70155..f617f4d 100644
--- a/model.go
+++ b/model.go
@@ -34,12 +34,11 @@ type Vault interface {
// User represents a user that should be able to send emails. This struct is
// found in the users json file, that is on the path pointed by VaultFile field
-// in [Config]. PrivateKey is the path to a private key for the DKIM signature.
+// in [Config].
type User struct {
Name string
Email string
Password string
- PrivateKey string
}
type store struct {