185 lines
4.4 KiB
Go
Executable File
185 lines
4.4 KiB
Go
Executable File
package email
|
|
|
|
import (
|
|
"fmt"
|
|
"net/smtp"
|
|
"os"
|
|
"testing"
|
|
|
|
"github.com/joho/godotenv"
|
|
"github.com/kelseyhightower/envconfig"
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/require"
|
|
)
|
|
|
|
type config struct {
|
|
MailUser string `required:"false" split_words:"true"`
|
|
MailPassword string `required:"false" split_words:"true"`
|
|
MailHost string `required:"false" split_words:"true"`
|
|
MailPort string `required:"false" split_words:"true"`
|
|
MailFrom string `required:"false" split_words:"true"`
|
|
MailTo string `required:"false" split_words:"true"`
|
|
}
|
|
|
|
func newConfig(envFile string) *config {
|
|
if envFile != "" {
|
|
err := godotenv.Load(envFile)
|
|
if err != nil {
|
|
panic(fmt.Errorf("godotenv.Load: %w", err))
|
|
}
|
|
}
|
|
|
|
cfg := &config{}
|
|
err := envconfig.Process("", cfg)
|
|
if err != nil {
|
|
panic(fmt.Errorf("envconfig.Process: %w", err))
|
|
}
|
|
|
|
return cfg
|
|
}
|
|
|
|
func TestNewConfig_MissingEnvFile(t *testing.T) {
|
|
assert.Panics(t, func() { newConfig(".missing_env_file") })
|
|
}
|
|
|
|
func TestMockSendEmail(t *testing.T) {
|
|
service := NewMockMailService(func(params ...interface{}) {})
|
|
|
|
emailData := EmailMessage{
|
|
To: "test@example.com",
|
|
Subject: "Test Email",
|
|
Body: "This is a test email.",
|
|
}
|
|
|
|
err := service.SendEmail(emailData)
|
|
if err != nil {
|
|
t.Fatalf("expected no error, got %v", err)
|
|
}
|
|
}
|
|
|
|
func TestNewInsecure(t *testing.T) {
|
|
cfg := newConfig(".env.test")
|
|
|
|
mailSrv := NewInsecure(MailServiceConfig{
|
|
Auth: smtp.PlainAuth("", cfg.MailUser, cfg.MailPassword, cfg.MailHost),
|
|
Host: cfg.MailHost,
|
|
Port: cfg.MailPort,
|
|
From: cfg.MailFrom,
|
|
})
|
|
|
|
t.Run("TestSendEmail", func(t *testing.T) {
|
|
data := EmailMessage{
|
|
To: cfg.MailTo,
|
|
Subject: "Mail Sender",
|
|
Body: "Hello this is a test email",
|
|
}
|
|
require.NoError(t, mailSrv.SendEmail(data))
|
|
})
|
|
|
|
t.Run("TestSendEmailWithAttachments", func(t *testing.T) {
|
|
reader, err := os.Open("testdata/attachment1.txt")
|
|
require.NoError(t, err)
|
|
defer reader.Close()
|
|
|
|
reader2, err := os.Open("testdata/attachment2.txt")
|
|
require.NoError(t, err)
|
|
defer reader2.Close()
|
|
|
|
reader3, err := os.Open("testdata/attachment3.txt")
|
|
require.NoError(t, err)
|
|
defer reader3.Close()
|
|
|
|
data := EmailMessage{
|
|
To: cfg.MailTo,
|
|
Subject: "Mail Sender",
|
|
Body: "Hello this is a test email",
|
|
Attachments: []EmailAttachment{
|
|
{
|
|
Title: "attachment1.txt",
|
|
File: reader,
|
|
},
|
|
{
|
|
Title: "attachment2.txt",
|
|
File: reader2,
|
|
},
|
|
{
|
|
Title: "attachment3.txt",
|
|
File: reader3,
|
|
},
|
|
},
|
|
}
|
|
err = mailSrv.SendEmail(data)
|
|
require.NoError(t, err)
|
|
})
|
|
|
|
t.Run("TestWithAttachments", func(t *testing.T) {
|
|
msg := newMessage("from", "to", "subject")
|
|
content, err := msg.withAttachments("body", nil)
|
|
require.NoError(t, err)
|
|
assert.Greater(t, len(content), 0)
|
|
})
|
|
|
|
t.Run("TestSendEmail_InvalidRecipient", func(t *testing.T) {
|
|
data := EmailMessage{
|
|
To: "invalid_email",
|
|
Subject: "Test Email",
|
|
Body: "This is a test email.",
|
|
}
|
|
err := mailSrv.SendEmail(data)
|
|
assert.Error(t, err)
|
|
})
|
|
|
|
t.Run("TestSendEmail_FailedAuthentication", func(t *testing.T) {
|
|
// set up authentication to fail
|
|
mailSrv := NewInsecure(MailServiceConfig{
|
|
Auth: smtp.PlainAuth("", "wronguser", "wrongpassword", cfg.MailHost),
|
|
Host: cfg.MailHost,
|
|
Port: cfg.MailPort,
|
|
From: cfg.MailFrom,
|
|
})
|
|
data := EmailMessage{
|
|
To: cfg.MailTo,
|
|
Subject: "Test Email",
|
|
Body: "This is a test email.",
|
|
}
|
|
err := mailSrv.SendEmail(data)
|
|
assert.Error(t, err)
|
|
})
|
|
}
|
|
|
|
func TestSecure(t *testing.T) {
|
|
cfg := newConfig(".env.test")
|
|
|
|
emailService := NewSecure(MailServiceConfig{
|
|
Auth: smtp.PlainAuth("", cfg.MailUser, cfg.MailPassword, cfg.MailHost),
|
|
Host: cfg.MailHost,
|
|
Port: cfg.MailPort,
|
|
From: cfg.MailFrom,
|
|
})
|
|
|
|
// Assert that the tls.Config is set up correctly
|
|
assert.NotNil(t, emailService.tlsconfig)
|
|
assert.True(t, emailService.tlsconfig.InsecureSkipVerify)
|
|
assert.Equal(t, cfg.MailHost, emailService.tlsconfig.ServerName)
|
|
assert.NotNil(t, emailService.tlsconfig.VerifyConnection)
|
|
|
|
t.Run("TestSendEmail", func(t *testing.T) {
|
|
// Mock the client and test the StartTLS method
|
|
var called bool
|
|
mockDialFn := func(hostPort string) (SMTPClientIface, error) {
|
|
called = true
|
|
return &mockSMTP{}, nil
|
|
}
|
|
emailService.dial = mockDialFn
|
|
|
|
data := EmailMessage{
|
|
To: cfg.MailTo,
|
|
Subject: "Mail Sender",
|
|
Body: "Hello this is a test email",
|
|
}
|
|
require.NoError(t, emailService.SendEmail(data))
|
|
assert.Equal(t, true, called)
|
|
})
|
|
|
|
}
|