feat: publish standalone worker
Separate worker packaging and service lifecycle from the control plane.
Этот коммит содержится в:
57
internal/notify/email.go
Обычный файл
57
internal/notify/email.go
Обычный файл
@@ -0,0 +1,57 @@
|
||||
// Package notify delivers notifications using credentials persisted in the
|
||||
// notification_credentials table. It is the credential-backed counterpart to
|
||||
// the legacy secrets.yml driven senders in internal/sender and internal/tg.
|
||||
package notify
|
||||
|
||||
import (
|
||||
"crypto/tls"
|
||||
"fmt"
|
||||
|
||||
"gopkg.in/gomail.v2"
|
||||
|
||||
"rsgit.ru/rsmon/rsmon/app/models"
|
||||
)
|
||||
|
||||
// Email sends an email using the given SMTP credential. bodyText is sent as
|
||||
// text/plain and, when non-empty, bodyHTML is added as a text/html alternative
|
||||
// so the recipient's MUA picks the best representation.
|
||||
func Email(cred *models.NotificationCredential, to, subject, bodyText, bodyHTML string) error {
|
||||
if cred == nil {
|
||||
return fmt.Errorf("credential is nil")
|
||||
}
|
||||
if cred.Kind != models.CredentialKindSMTP {
|
||||
return fmt.Errorf("credential %d is not smtp (kind=%s)", cred.ID, cred.Kind)
|
||||
}
|
||||
if cred.Server == nil || cred.Port == nil || cred.Login == nil || cred.FromAddr == nil {
|
||||
return fmt.Errorf("credential %d missing required smtp fields", cred.ID)
|
||||
}
|
||||
|
||||
password, err := cred.GetSecret()
|
||||
if err != nil {
|
||||
return fmt.Errorf("decrypt smtp password: %w", err)
|
||||
}
|
||||
|
||||
fromName := "RSMon"
|
||||
if cred.FromName != nil && *cred.FromName != "" {
|
||||
fromName = *cred.FromName
|
||||
}
|
||||
|
||||
m := gomail.NewMessage()
|
||||
m.SetHeader("From", m.FormatAddress(*cred.FromAddr, fromName))
|
||||
m.SetHeader("To", to)
|
||||
m.SetHeader("Subject", subject)
|
||||
m.AddAlternative("text/plain", bodyText)
|
||||
if bodyHTML != "" {
|
||||
m.AddAlternative("text/html", bodyHTML)
|
||||
}
|
||||
|
||||
d := gomail.NewDialer(*cred.Server, *cred.Port, *cred.Login, password)
|
||||
if cred.InsecureSkipVerify {
|
||||
d.TLSConfig = &tls.Config{InsecureSkipVerify: true}
|
||||
}
|
||||
|
||||
if err := d.DialAndSend(m); err != nil {
|
||||
return fmt.Errorf("send smtp via credential %d: %w", cred.ID, err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
Ссылка в новой задаче
Block a user