1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
|
package smtp
import (
"crypto/tls"
"dove/config"
"dove/utils/logger"
"fmt"
"time"
gosmtp "github.com/emersion/go-smtp"
)
type ServerInstance struct {
Server *gosmtp.Server
Label string
}
var activeServers []ServerInstance
func Start() {
var tlsConfig *tls.Config
if config.SMTP.TLSEnabled {
tlsConfig = loadTLSConfig()
}
plainAddress := fmt.Sprintf("%s:%d", config.SMTP.Host, config.SMTP.Port)
plainServer := createServer(plainAddress)
activeServers = append(activeServers, ServerInstance{Server: plainServer, Label: "SMTP"})
go startListener(plainServer, "SMTP", plainAddress)
smtpsAddress := fmt.Sprintf("%s:%d", config.SMTP.Host, config.SMTP.SMTPSPort)
smtpsServer := createServer(smtpsAddress)
activeServers = append(activeServers, ServerInstance{Server: smtpsServer, Label: "SMTPS"})
if tlsConfig != nil {
smtpsServer.TLSConfig = tlsConfig
go startTLSListener(smtpsServer, "SMTPS", smtpsAddress)
} else {
go startListener(smtpsServer, "SMTPS", smtpsAddress)
}
starttlsAddress := fmt.Sprintf("%s:%d", config.SMTP.Host, config.SMTP.StartTLSPort)
starttlsServer := createServer(starttlsAddress)
starttlsServer.EnableSMTPUTF8 = true
activeServers = append(activeServers, ServerInstance{Server: starttlsServer, Label: "STARTTLS"})
if tlsConfig != nil {
starttlsServer.TLSConfig = tlsConfig
}
go startListener(starttlsServer, "STARTTLS", starttlsAddress)
}
func Shutdown() {
for _, instance := range activeServers {
if shutdownError := instance.Server.Close(); shutdownError != nil {
logger.Errorf(LogPrefix, ShutdownFailed, instance.Label, shutdownError)
}
}
logger.Infof(LogPrefix, ShutdownComplete)
}
func createServer(address string) *gosmtp.Server {
smtpServer := gosmtp.NewServer(gosmtp.BackendFunc(func(connection *gosmtp.Conn) (gosmtp.Session, error) {
logger.Debugf(LogPrefix, SessionStarted, connection.Hostname())
return &Session{}, nil
}))
smtpServer.Addr = address
smtpServer.Domain = config.SMTP.Domain
smtpServer.ReadTimeout = time.Duration(config.SMTP.ReadTimeout) * time.Second
smtpServer.WriteTimeout = time.Duration(config.SMTP.WriteTimeout) * time.Second
smtpServer.MaxMessageBytes = int64(config.SMTP.MaxMessageSize)
smtpServer.AllowInsecureAuth = true
return smtpServer
}
func loadTLSConfig() *tls.Config {
certificate, loadError := tls.LoadX509KeyPair(config.SMTP.TLSCertPath, config.SMTP.TLSKeyPath)
if loadError != nil {
logger.Errorf(LogPrefix, TLSCertLoadFailed, loadError)
return nil
}
return &tls.Config{
Certificates: []tls.Certificate{certificate},
}
}
func startListener(smtpServer *gosmtp.Server, label string, address string) {
logger.Successf(LogPrefix, ServerStarting, label, address)
if listenError := smtpServer.ListenAndServe(); listenError != nil {
logger.Fatalf(LogPrefix, ListenFailed, label, listenError)
}
}
func startTLSListener(smtpServer *gosmtp.Server, label string, address string) {
logger.Successf(LogPrefix, ServerStarting, label, address)
if listenError := smtpServer.ListenAndServeTLS(); listenError != nil {
logger.Fatalf(LogPrefix, ListenFailed, label, listenError)
}
}
|