diff --git a/config/config.go b/config/config.go index 942afd4..878a7bb 100644 --- a/config/config.go +++ b/config/config.go @@ -58,6 +58,14 @@ type AmConfig struct { Driver string `yaml:"driver"` Dsn string `yaml:"dsn"` } `yaml:"database"` + Email struct { + Host string `yaml:"host"` + Port int `yaml:"port"` + Tls string `yaml:"tls"` + AuthType string `yaml:"authType"` + User string `yaml:"user"` + Password string `yaml:"password"` + } `yaml:"email"` Rendering struct { TemplateDir string `yaml:"templatedir"` CookieKey string `yaml:"cookiekey"` @@ -114,6 +122,12 @@ func overlayConfig(dest *AmConfig, loaded *AmConfig, defaults *AmConfig) { dest.Site.UserAgreement.Text = overlayString(loaded.Site.UserAgreement.Text, defaults.Site.UserAgreement.Text) dest.Database.Driver = overlayString(loaded.Database.Driver, defaults.Database.Driver) dest.Database.Dsn = overlayString(loaded.Database.Dsn, defaults.Database.Dsn) + dest.Email.Host = overlayString(loaded.Email.Host, defaults.Email.Host) + dest.Email.Port = overlayInt(loaded.Email.Port, defaults.Email.Port) + dest.Email.Tls = overlayString(loaded.Email.Tls, defaults.Email.Tls) + dest.Email.AuthType = overlayString(loaded.Email.AuthType, defaults.Email.AuthType) + dest.Email.User = overlayString(loaded.Email.User, defaults.Email.User) + dest.Email.Password = overlayString(loaded.Email.Password, defaults.Email.Password) dest.Rendering.TemplateDir = overlayString(loaded.Rendering.TemplateDir, defaults.Rendering.TemplateDir) dest.Rendering.CookieKey = overlayString(loaded.Rendering.CookieKey, defaults.Rendering.CookieKey) } diff --git a/config/default.yaml b/config/default.yaml index 198f703..af4f5e1 100644 --- a/config/default.yaml +++ b/config/default.yaml @@ -16,6 +16,13 @@ site: database: driver: "mysql" dsn: "amsdb:x00yes2k@tcp(localhost)/amsterdam?parseTime=true&loc=Local" +email: + host: smtp.example.com + port: 587 + tls: starttls + authType: plain + user: jrn + password: foobiebletch rendering: templatedir: custom_templates cookiekey: ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz diff --git a/email/message.go b/email/message.go new file mode 100644 index 0000000..611dcfe --- /dev/null +++ b/email/message.go @@ -0,0 +1,75 @@ +/* + * Amsterdam Web Communities System + * Copyright (c) 2025 Erbosoft Metaverse Design Solutions, All Rights Reserved + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. + */ + +// Package email contains support for E-mail messages sent by Amsterdam. +package email + +import "fmt" + +// Message is the interface for an E-mail message to be sent. +type Message interface { + SetFrom(string, string) + AddTo(string, string) + AddCC(string, string) + AddBCC(string, string) + SetSubject(string) + SetText(string) + AddHeader(string, string) +} + +type amMessage struct { + from string + to []string + cc []string + bcc []string + subject string + text string + headers map[string]string +} + +func formatAddress(addr string, name string) string { + if name == "" { + return addr + } else { + return fmt.Sprintf("%s <%s>", name, addr) + } +} + +func (m *amMessage) SetFrom(addr string, name string) { + m.from = formatAddress(addr, name) +} + +func (m *amMessage) AddTo(addr string, name string) { + m.to = append(m.to, formatAddress(addr, name)) +} + +func (m *amMessage) AddCC(addr string, name string) { + m.cc = append(m.cc, formatAddress(addr, name)) +} + +func (m *amMessage) AddBCC(addr string, name string) { + m.bcc = append(m.bcc, formatAddress(addr, name)) +} + +func (m *amMessage) SetSubject(s string) { + m.subject = s +} + +func (m *amMessage) SetText(txt string) { + m.text = txt +} + +func (m *amMessage) AddHeader(name string, value string) { + m.headers[name] = value +} + +func AmNewEmailMessage() Message { + rc := amMessage{to: make([]string, 0), cc: make([]string, 0), bcc: make([]string, 0), headers: make(map[string]string)} + return &rc +}