Files
galaxy-game/authsession/internal/testkit/mail_sender.go
T
2026-04-08 16:23:07 +02:00

74 lines
1.8 KiB
Go

package testkit
import (
"context"
"sync"
"galaxy/authsession/internal/ports"
)
// RecordingMailSender is a deterministic MailSender double that records every
// delivery request and returns preconfigured outcomes or errors.
type RecordingMailSender struct {
mu sync.Mutex
// Results stores queued results consumed by SendLoginCode before
// DefaultResult is used.
Results []ports.SendLoginCodeResult
// DefaultResult stores the result used when Results is empty.
DefaultResult ports.SendLoginCodeResult
// Err is returned directly from SendLoginCode when set.
Err error
recordedInputs []ports.SendLoginCodeInput
}
// SendLoginCode records input and returns the next configured result.
func (s *RecordingMailSender) SendLoginCode(ctx context.Context, input ports.SendLoginCodeInput) (ports.SendLoginCodeResult, error) {
if err := ctx.Err(); err != nil {
return ports.SendLoginCodeResult{}, err
}
if err := input.Validate(); err != nil {
return ports.SendLoginCodeResult{}, err
}
s.mu.Lock()
defer s.mu.Unlock()
s.recordedInputs = append(s.recordedInputs, input)
if s.Err != nil {
return ports.SendLoginCodeResult{}, s.Err
}
if len(s.Results) > 0 {
result := s.Results[0]
s.Results = s.Results[1:]
if err := result.Validate(); err != nil {
return ports.SendLoginCodeResult{}, err
}
return result, nil
}
result := s.DefaultResult
if result.Outcome == "" {
result.Outcome = ports.SendLoginCodeOutcomeSent
}
if err := result.Validate(); err != nil {
return ports.SendLoginCodeResult{}, err
}
return result, nil
}
// RecordedInputs returns a stable snapshot of every recorded mail request.
func (s *RecordingMailSender) RecordedInputs() []ports.SendLoginCodeInput {
s.mu.Lock()
defer s.mu.Unlock()
return append([]ports.SendLoginCodeInput(nil), s.recordedInputs...)
}
var _ ports.MailSender = (*RecordingMailSender)(nil)