mirror of
https://github.com/foxcpp/maddy.git
synced 2025-04-06 06:27:38 +03:00
Rename dispatcher to "msgpipeline"
New name more precisely describes what it is doing now. It was initally meant to be more generic and usable for other purposes, but I don't think we will need that flexibility.
This commit is contained in:
parent
9d3b7f15a4
commit
028d8b914c
18 changed files with 311 additions and 311 deletions
|
@ -19,12 +19,12 @@ import (
|
|||
"github.com/foxcpp/maddy/buffer"
|
||||
"github.com/foxcpp/maddy/config"
|
||||
modconfig "github.com/foxcpp/maddy/config/module"
|
||||
"github.com/foxcpp/maddy/dispatcher"
|
||||
"github.com/foxcpp/maddy/dns"
|
||||
"github.com/foxcpp/maddy/endpoint"
|
||||
"github.com/foxcpp/maddy/future"
|
||||
"github.com/foxcpp/maddy/log"
|
||||
"github.com/foxcpp/maddy/module"
|
||||
"github.com/foxcpp/maddy/msgpipeline"
|
||||
"github.com/foxcpp/maddy/target"
|
||||
)
|
||||
|
||||
|
@ -70,7 +70,7 @@ func (s *Session) Reset() {
|
|||
|
||||
func (s *Session) Mail(from string) error {
|
||||
var err error
|
||||
s.msgMeta.ID, err = dispatcher.GenerateMsgID()
|
||||
s.msgMeta.ID, err = msgpipeline.GenerateMsgID()
|
||||
if err != nil {
|
||||
s.endp.Log.Printf("rand.Rand error: %v", err)
|
||||
return s.wrapErr(errInternal)
|
||||
|
@ -90,7 +90,7 @@ func (s *Session) Mail(from string) error {
|
|||
}
|
||||
|
||||
if !s.endp.deferServerReject {
|
||||
s.delivery, err = s.endp.dispatcher.Start(s.msgMeta, s.msgMeta.OriginalFrom)
|
||||
s.delivery, err = s.endp.pipeline.Start(s.msgMeta, s.msgMeta.OriginalFrom)
|
||||
if err != nil {
|
||||
s.log.Printf("sender rejected: %v", err)
|
||||
return s.wrapErr(err)
|
||||
|
@ -125,7 +125,7 @@ func (s *Session) Rcpt(to string) error {
|
|||
}
|
||||
|
||||
var err error
|
||||
s.delivery, err = s.endp.dispatcher.Start(s.msgMeta, s.msgMeta.OriginalFrom)
|
||||
s.delivery, err = s.endp.pipeline.Start(s.msgMeta, s.msgMeta.OriginalFrom)
|
||||
if err != nil {
|
||||
s.log.Printf("sender rejected (deferred): %v, RCPT TO = %s", err, to)
|
||||
s.deliveryErr = err
|
||||
|
@ -219,7 +219,7 @@ type Endpoint struct {
|
|||
name string
|
||||
aliases []string
|
||||
listeners []net.Listener
|
||||
dispatcher *dispatcher.Dispatcher
|
||||
pipeline *msgpipeline.MsgPipeline
|
||||
resolver dns.Resolver
|
||||
|
||||
authAlwaysRequired bool
|
||||
|
@ -320,12 +320,12 @@ func (endp *Endpoint) setConfig(cfg *config.Map) error {
|
|||
if err != nil {
|
||||
return err
|
||||
}
|
||||
endp.dispatcher, err = dispatcher.NewDispatcher(cfg.Globals, unmatched)
|
||||
endp.pipeline, err = msgpipeline.New(cfg.Globals, unmatched)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
endp.dispatcher.Hostname = endp.serv.Domain
|
||||
endp.dispatcher.Log = log.Logger{Name: "smtp/dispatcher", Debug: endp.Log.Debug}
|
||||
endp.pipeline.Hostname = endp.serv.Domain
|
||||
endp.pipeline.Log = log.Logger{Name: "smtp/pipeline", Debug: endp.Log.Debug}
|
||||
|
||||
// endp.submission can be set to true by New, leave it on
|
||||
// even if directive is missing.
|
||||
|
|
|
@ -462,10 +462,10 @@ imaps://127.0.0.1:143
|
|||
imap://0.0.0.0
|
||||
```
|
||||
|
||||
# DISPATCHING DIRECTIVES
|
||||
# PIPELINE DIRECTIVES
|
||||
|
||||
maddy have a generic framework for message filtering and simple
|
||||
per-sender/per-recipient routing dispatcher.
|
||||
per-sender/per-recipient routing.
|
||||
|
||||
Below are directives you can use in the configuration of the modules that
|
||||
act as a message sources (e.g. a SMTP endpoint).
|
||||
|
@ -680,8 +680,8 @@ Enable verbose logging only for this configuration block.
|
|||
ESMTP server endpoint. Endpoints are special-case modules that use config
|
||||
directive arguments to specify listening addresses.
|
||||
|
||||
See DISPATCHING DIRECTIVES for the description of the
|
||||
conditional message dispatching and filtering configuration.
|
||||
See PIPELINE DIRECTIVES for the description of the
|
||||
conditional message routing and filtering configuration.
|
||||
|
||||
```
|
||||
smtp smtp://0.0.0.0:25 smtps://0.0.0.0:587 {
|
||||
|
@ -744,7 +744,7 @@ for all operations. You should use it for Submission protocol endpoints.
|
|||
|
||||
## defer_sender_reject [yes/no]
|
||||
|
||||
Run sender-based checks and dispatching logic when first RCPT TO command
|
||||
Apply sender-based checks and routing logic when first RCPT TO command
|
||||
is received. This allows maddy to log recipient address of the rejected
|
||||
message and also improves interoperability with (improperly implemented)
|
||||
clients that don't expect an error early in session.
|
||||
|
@ -890,7 +890,7 @@ Default is 4.
|
|||
|
||||
The block specified with the bounce directive specifies how DSN (Delivery Status Notification)
|
||||
messages should be routed. The syntax of directives inside this block is described in
|
||||
DISPATCHING DIRECTIVES section.
|
||||
PIPELINE DIRECTIVES section.
|
||||
|
||||
If this is block is not present in configuration, DSNs will not be generated. Note, however,
|
||||
this is not what you want most of the time.
|
||||
|
|
|
@ -50,11 +50,11 @@ type CheckResult struct {
|
|||
// is considered "possibly malicious" and should be
|
||||
// put into Junk mailbox.
|
||||
//
|
||||
// This value is copied into MsgMetadata by the dispatcher.
|
||||
// This value is copied into MsgMetadata by the msgpipeline.
|
||||
Quarantine bool
|
||||
|
||||
// ScoreAdjust is the value that is added to the MsgMetadata.CheckScore
|
||||
// by the dispatcher after check execution.
|
||||
// by the msgpipeline after check execution.
|
||||
ScoreAdjust int32
|
||||
|
||||
// AuthResult is the information that is supposed to
|
||||
|
|
|
@ -33,7 +33,7 @@ type ModifierState interface {
|
|||
// argument, otherwise it returns a new value.
|
||||
//
|
||||
// Note that per-source/per-destination modifiers are executed
|
||||
// after dispatching decision is made so changed value will have no
|
||||
// after routing decision is made so changed value will have no
|
||||
// effect on it.
|
||||
//
|
||||
// Also note that MsgMeta.OriginalFrom will still contain the original value
|
||||
|
@ -44,7 +44,7 @@ type ModifierState interface {
|
|||
// If no changed are required, this method returns its argument, otherwise
|
||||
// it returns a new value.
|
||||
//
|
||||
// Dispatcher will take of populating MsgMeta.OriginalRcpts. RewriteRcpt
|
||||
// MsgPipeline will take of populating MsgMeta.OriginalRcpts. RewriteRcpt
|
||||
// doesn't do it.
|
||||
RewriteRcpt(rcptTo string) (string, error)
|
||||
|
||||
|
|
|
@ -89,13 +89,13 @@ type MsgMetadata struct {
|
|||
// in the storage.
|
||||
//
|
||||
// This field should not be modified by the checks that verify
|
||||
// the message. It is set only by the message dispatcher.
|
||||
// the message. It is set only by the message msgpipeline.
|
||||
Quarantine bool
|
||||
|
||||
// OriginalRcpts contains the mapping from the final recipient to the
|
||||
// recipient that was presented by the client.
|
||||
//
|
||||
// Dispatcher will update that field when recipient modifiers
|
||||
// MsgPipeline will update that field when recipient modifiers
|
||||
// are executed.
|
||||
//
|
||||
// It should be used when reporting information back to client (via DSN,
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"strconv"
|
||||
|
@ -8,9 +8,9 @@ import (
|
|||
"github.com/foxcpp/maddy/testutils"
|
||||
)
|
||||
|
||||
func BenchmarkDispatcherSimple(b *testing.B) {
|
||||
func BenchmarkMsgPipelineSimple(b *testing.B) {
|
||||
target := testutils.Target{InstName: "test_target", DiscardMessages: true}
|
||||
d := Dispatcher{dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -23,7 +23,7 @@ func BenchmarkDispatcherSimple(b *testing.B) {
|
|||
testutils.BenchDelivery(b, &d, "sender@example.org", []string{"rcpt-X@example.org"})
|
||||
}
|
||||
|
||||
func BenchmarkDispatcherGlobalChecks(b *testing.B) {
|
||||
func BenchmarkMsgPipelineGlobalChecks(b *testing.B) {
|
||||
testWithCount := func(checksCount int) {
|
||||
b.Run(strconv.Itoa(checksCount), func(b *testing.B) {
|
||||
checks := make([]module.Check, 0, checksCount)
|
||||
|
@ -32,7 +32,7 @@ func BenchmarkDispatcherGlobalChecks(b *testing.B) {
|
|||
}
|
||||
|
||||
target := testutils.Target{InstName: "test_target", DiscardMessages: true}
|
||||
d := Dispatcher{dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: checks,
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -52,7 +52,7 @@ func BenchmarkDispatcherGlobalChecks(b *testing.B) {
|
|||
testWithCount(15)
|
||||
}
|
||||
|
||||
func BenchmarkDispatcherTargets(b *testing.B) {
|
||||
func BenchmarkMsgPipelineTargets(b *testing.B) {
|
||||
testWithCount := func(targetCount int) {
|
||||
b.Run(strconv.Itoa(targetCount), func(b *testing.B) {
|
||||
targets := make([]module.DeliveryTarget, 0, targetCount)
|
||||
|
@ -60,7 +60,7 @@ func BenchmarkDispatcherTargets(b *testing.B) {
|
|||
targets = append(targets, &testutils.Target{InstName: "target_" + strconv.Itoa(i), DiscardMessages: true})
|
||||
}
|
||||
|
||||
d := Dispatcher{dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
@ -15,7 +15,7 @@ func (m multipleErrs) SetStatus(rcptTo string, err error) {
|
|||
m[rcptTo] = err
|
||||
}
|
||||
|
||||
func TestDispatcher_BodyNonAtomic(t *testing.T) {
|
||||
func TestMsgPipeline_BodyNonAtomic(t *testing.T) {
|
||||
err := errors.New("go away")
|
||||
|
||||
target := testutils.Target{
|
||||
|
@ -23,8 +23,8 @@ func TestDispatcher_BodyNonAtomic(t *testing.T) {
|
|||
"tester@example.org": err,
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -33,7 +33,7 @@ func TestDispatcher_BodyNonAtomic(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
c := multipleErrs{}
|
||||
|
@ -47,7 +47,7 @@ func TestDispatcher_BodyNonAtomic(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_BodyNonAtomic_ModifiedRcpt(t *testing.T) {
|
||||
func TestMsgPipeline_BodyNonAtomic_ModifiedRcpt(t *testing.T) {
|
||||
err := errors.New("go away")
|
||||
|
||||
target := testutils.Target{
|
||||
|
@ -55,8 +55,8 @@ func TestDispatcher_BodyNonAtomic_ModifiedRcpt(t *testing.T) {
|
|||
"tester-alias@example.org": err,
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{
|
||||
testutils.Modifier{
|
||||
|
@ -75,7 +75,7 @@ func TestDispatcher_BodyNonAtomic_ModifiedRcpt(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
c := multipleErrs{}
|
||||
|
@ -89,7 +89,7 @@ func TestDispatcher_BodyNonAtomic_ModifiedRcpt(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_BodyNonAtomic_ExpandAtomic(t *testing.T) {
|
||||
func TestMsgPipeline_BodyNonAtomic_ExpandAtomic(t *testing.T) {
|
||||
err := errors.New("go away")
|
||||
|
||||
target, target2 := testutils.Target{
|
||||
|
@ -99,8 +99,8 @@ func TestDispatcher_BodyNonAtomic_ExpandAtomic(t *testing.T) {
|
|||
}, testutils.Target{
|
||||
BodyErr: err,
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -109,7 +109,7 @@ func TestDispatcher_BodyNonAtomic_ExpandAtomic(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
c := multipleErrs{}
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"fmt"
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
@ -10,15 +10,15 @@ import (
|
|||
"github.com/foxcpp/maddy/testutils"
|
||||
)
|
||||
|
||||
func TestDispatcher_NoScoresChecked(t *testing.T) {
|
||||
func TestMsgPipeline_NoScoresChecked(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}, testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -28,7 +28,7 @@ func TestDispatcher_NoScoresChecked(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// No rejectScore or quarantineScore.
|
||||
|
@ -46,7 +46,7 @@ func TestDispatcher_NoScoresChecked(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RejectScore(t *testing.T) {
|
||||
func TestMsgPipeline_RejectScore(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -54,8 +54,8 @@ func TestDispatcher_RejectScore(t *testing.T) {
|
|||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}
|
||||
rejectScore := 10
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -66,7 +66,7 @@ func TestDispatcher_RejectScore(t *testing.T) {
|
|||
},
|
||||
rejectScore: &rejectScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be rejected.
|
||||
|
@ -83,7 +83,7 @@ func TestDispatcher_RejectScore(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RejectScore_notEnough(t *testing.T) {
|
||||
func TestMsgPipeline_RejectScore_notEnough(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -91,8 +91,8 @@ func TestDispatcher_RejectScore_notEnough(t *testing.T) {
|
|||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}
|
||||
rejectScore := 15
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -103,7 +103,7 @@ func TestDispatcher_RejectScore_notEnough(t *testing.T) {
|
|||
},
|
||||
rejectScore: &rejectScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "whatever@whatever", []string{"whatever@whatever"})
|
||||
|
@ -120,15 +120,15 @@ func TestDispatcher_RejectScore_notEnough(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_Quarantine(t *testing.T) {
|
||||
func TestMsgPipeline_Quarantine(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{},
|
||||
}, testutils.Check{
|
||||
BodyRes: module.CheckResult{Quarantine: true},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -138,7 +138,7 @@ func TestDispatcher_Quarantine(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be quarantined.
|
||||
|
@ -156,7 +156,7 @@ func TestDispatcher_Quarantine(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_QuarantineScore(t *testing.T) {
|
||||
func TestMsgPipeline_QuarantineScore(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -164,8 +164,8 @@ func TestDispatcher_QuarantineScore(t *testing.T) {
|
|||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}
|
||||
quarantineScore := 10
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -176,7 +176,7 @@ func TestDispatcher_QuarantineScore(t *testing.T) {
|
|||
},
|
||||
quarantineScore: &quarantineScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be quarantined.
|
||||
|
@ -194,7 +194,7 @@ func TestDispatcher_QuarantineScore(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_QuarantineScore_notEnough(t *testing.T) {
|
||||
func TestMsgPipeline_QuarantineScore_notEnough(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -202,8 +202,8 @@ func TestDispatcher_QuarantineScore_notEnough(t *testing.T) {
|
|||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
}
|
||||
quarantineScore := 15
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -214,7 +214,7 @@ func TestDispatcher_QuarantineScore_notEnough(t *testing.T) {
|
|||
},
|
||||
quarantineScore: &quarantineScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be quarantined.
|
||||
|
@ -232,7 +232,7 @@ func TestDispatcher_QuarantineScore_notEnough(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_BothScores_Quarantined(t *testing.T) {
|
||||
func TestMsgPipeline_BothScores_Quarantined(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -241,8 +241,8 @@ func TestDispatcher_BothScores_Quarantined(t *testing.T) {
|
|||
}
|
||||
quarantineScore := 10
|
||||
rejectScore := 15
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -254,7 +254,7 @@ func TestDispatcher_BothScores_Quarantined(t *testing.T) {
|
|||
quarantineScore: &quarantineScore,
|
||||
rejectScore: &rejectScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be quarantined.
|
||||
|
@ -272,7 +272,7 @@ func TestDispatcher_BothScores_Quarantined(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_BothScores_Rejected(t *testing.T) {
|
||||
func TestMsgPipeline_BothScores_Rejected(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{ScoreAdjust: 5},
|
||||
|
@ -281,8 +281,8 @@ func TestDispatcher_BothScores_Rejected(t *testing.T) {
|
|||
}
|
||||
quarantineScore := 5
|
||||
rejectScore := 10
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -294,7 +294,7 @@ func TestDispatcher_BothScores_Rejected(t *testing.T) {
|
|||
quarantineScore: &quarantineScore,
|
||||
rejectScore: &rejectScore,
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Should be quarantined.
|
||||
|
@ -311,7 +311,7 @@ func TestDispatcher_BothScores_Rejected(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_AuthResults(t *testing.T) {
|
||||
func TestMsgPipeline_AuthResults(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check1, check2 := testutils.Check{
|
||||
BodyRes: module.CheckResult{
|
||||
|
@ -334,8 +334,8 @@ func TestDispatcher_AuthResults(t *testing.T) {
|
|||
},
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -346,7 +346,7 @@ func TestDispatcher_AuthResults(t *testing.T) {
|
|||
},
|
||||
},
|
||||
Hostname: "TEST-HOST",
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "whatever@whatever", []string{"whatever@whatever"})
|
||||
|
@ -394,7 +394,7 @@ func TestDispatcher_AuthResults(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_Headers(t *testing.T) {
|
||||
func TestMsgPipeline_Headers(t *testing.T) {
|
||||
hdr1 := textproto.Header{}
|
||||
hdr1.Add("HDR1", "1")
|
||||
hdr2 := textproto.Header{}
|
||||
|
@ -410,8 +410,8 @@ func TestDispatcher_Headers(t *testing.T) {
|
|||
Header: hdr2,
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check1, &check2},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -422,7 +422,7 @@ func TestDispatcher_Headers(t *testing.T) {
|
|||
},
|
||||
},
|
||||
Hostname: "TEST-HOST",
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "whatever@whatever", []string{"whatever@whatever"})
|
||||
|
@ -443,7 +443,7 @@ func TestDispatcher_Headers(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_Globalcheck_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_Globalcheck_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check_ := testutils.Check{
|
||||
InitErr: errors.New("1"),
|
||||
|
@ -452,8 +452,8 @@ func TestDispatcher_Globalcheck_Errors(t *testing.T) {
|
|||
RcptRes: module.CheckResult{RejectErr: errors.New("4")},
|
||||
BodyRes: module.CheckResult{RejectErr: errors.New("5")},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&check_},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -464,7 +464,7 @@ func TestDispatcher_Globalcheck_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
Hostname: "TEST-HOST",
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
||||
|
@ -521,7 +521,7 @@ func TestDispatcher_Globalcheck_Errors(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SourceCheck_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_SourceCheck_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check_ := testutils.Check{
|
||||
InitErr: errors.New("1"),
|
||||
|
@ -531,8 +531,8 @@ func TestDispatcher_SourceCheck_Errors(t *testing.T) {
|
|||
BodyRes: module.CheckResult{RejectErr: errors.New("5")},
|
||||
}
|
||||
globalCheck := testutils.Check{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&globalCheck},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -544,7 +544,7 @@ func TestDispatcher_SourceCheck_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
Hostname: "TEST-HOST",
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
||||
|
@ -602,7 +602,7 @@ func TestDispatcher_SourceCheck_Errors(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_RcptCheck_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
check_ := testutils.Check{
|
||||
InitErr: errors.New("1"),
|
||||
|
@ -616,8 +616,8 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
// Added to check whether it leaks.
|
||||
globalCheck := testutils.Check{InstName: "global_check"}
|
||||
sourceCheck := testutils.Check{InstName: "source_check"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalChecks: []module.Check{&globalCheck},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -629,11 +629,11 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
Hostname: "TEST-HOST",
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
_, err := testutils.DoTestDeliveryErr(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
if err == nil {
|
||||
t.Fatal("expected error")
|
||||
|
@ -645,7 +645,7 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
check_.InitErr = nil
|
||||
|
||||
t.Run("conn err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
_, err := testutils.DoTestDeliveryErr(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
if err == nil {
|
||||
t.Fatal("expected error")
|
||||
|
@ -657,7 +657,7 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
check_.ConnRes.RejectErr = nil
|
||||
|
||||
t.Run("mail from err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
_, err := testutils.DoTestDeliveryErr(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
if err == nil {
|
||||
t.Fatal("expected error")
|
||||
|
@ -669,7 +669,7 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
check_.SenderRes.RejectErr = nil
|
||||
|
||||
t.Run("rcpt to err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
_, err := testutils.DoTestDeliveryErr(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
if err == nil {
|
||||
t.Fatal("expected error")
|
||||
|
@ -679,7 +679,7 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
check_.RcptRes.RejectErr = nil
|
||||
|
||||
t.Run("body err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
_, err := testutils.DoTestDeliveryErr(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
if err == nil {
|
||||
t.Fatal("expected error")
|
||||
|
@ -689,7 +689,7 @@ func TestDispatcher_RcptCheck_Errors(t *testing.T) {
|
|||
check_.BodyRes.RejectErr = nil
|
||||
|
||||
t.Run("no err", func(t *testing.T) {
|
||||
d.Log = testutils.Logger(t, "dispatcher")
|
||||
d.Log = testutils.Logger(t, "msgpipeline")
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
})
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
@ -13,7 +13,7 @@ import (
|
|||
"github.com/foxcpp/maddy/module"
|
||||
)
|
||||
|
||||
type dispatcherCfg struct {
|
||||
type msgpipelineCfg struct {
|
||||
globalChecks []module.Check
|
||||
globalModifiers modify.Group
|
||||
perSource map[string]sourceBlock
|
||||
|
@ -28,8 +28,8 @@ type dispatcherCfg struct {
|
|||
quarantineScore *int
|
||||
}
|
||||
|
||||
func parseDispatcherRootCfg(globals map[string]interface{}, nodes []config.Node) (dispatcherCfg, error) {
|
||||
cfg := dispatcherCfg{
|
||||
func parseMsgPipelineRootCfg(globals map[string]interface{}, nodes []config.Node) (msgpipelineCfg, error) {
|
||||
cfg := msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
}
|
||||
var defaultSrcRaw []config.Node
|
||||
|
@ -38,64 +38,64 @@ func parseDispatcherRootCfg(globals map[string]interface{}, nodes []config.Node)
|
|||
switch node.Name {
|
||||
case "check":
|
||||
if len(node.Children) == 0 {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "empty checks block")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "empty checks block")
|
||||
}
|
||||
|
||||
var err error
|
||||
cfg.globalChecks, err = parseChecksGroup(globals, node.Children)
|
||||
if err != nil {
|
||||
return dispatcherCfg{}, err
|
||||
return msgpipelineCfg{}, err
|
||||
}
|
||||
case "modify":
|
||||
if len(node.Children) == 0 {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "empty modifiers block")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "empty modifiers block")
|
||||
}
|
||||
|
||||
var err error
|
||||
cfg.globalModifiers, err = parseModifiersGroup(globals, node.Children)
|
||||
if err != nil {
|
||||
return dispatcherCfg{}, err
|
||||
return msgpipelineCfg{}, err
|
||||
}
|
||||
case "source":
|
||||
srcBlock, err := parseDispatcherSrcCfg(globals, node.Children)
|
||||
srcBlock, err := parseMsgPipelineSrcCfg(globals, node.Children)
|
||||
if err != nil {
|
||||
return dispatcherCfg{}, err
|
||||
return msgpipelineCfg{}, err
|
||||
}
|
||||
|
||||
if len(node.Args) == 0 {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "expected at least one source dispatch rule")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "expected at least one source matching rule")
|
||||
}
|
||||
|
||||
for _, rule := range node.Args {
|
||||
if !validDispatchRule(rule) {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "invalid source dispatch rule: %v", rule)
|
||||
if !validMatchRule(rule) {
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "invalid source routing rule: %v", rule)
|
||||
}
|
||||
|
||||
cfg.perSource[rule] = srcBlock
|
||||
}
|
||||
case "default_source":
|
||||
if defaultSrcRaw != nil {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "duplicate 'default_source' block")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "duplicate 'default_source' block")
|
||||
}
|
||||
defaultSrcRaw = node.Children
|
||||
case "quarantine_score":
|
||||
if len(node.Args) != 1 {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "exactly one argument required")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "exactly one argument required")
|
||||
}
|
||||
|
||||
quarantineScore, err := strconv.Atoi(node.Args[0])
|
||||
if err != nil {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "%v", err)
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "%v", err)
|
||||
}
|
||||
cfg.quarantineScore = &quarantineScore
|
||||
case "reject_score":
|
||||
if len(node.Args) != 1 {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "exactly one argument required")
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "exactly one argument required")
|
||||
}
|
||||
|
||||
rejectScore, err := strconv.Atoi(node.Args[0])
|
||||
if err != nil {
|
||||
return dispatcherCfg{}, config.NodeErr(&node, "%v", err)
|
||||
return msgpipelineCfg{}, config.NodeErr(&node, "%v", err)
|
||||
}
|
||||
cfg.rejectScore = &rejectScore
|
||||
default:
|
||||
|
@ -105,26 +105,26 @@ func parseDispatcherRootCfg(globals map[string]interface{}, nodes []config.Node)
|
|||
|
||||
if len(cfg.perSource) == 0 && len(defaultSrcRaw) == 0 {
|
||||
if len(othersRaw) == 0 {
|
||||
return dispatcherCfg{}, fmt.Errorf("empty dispatching configuration, use 'reject' to reject messages")
|
||||
return msgpipelineCfg{}, fmt.Errorf("empty pipeline configuration, use 'reject' to reject messages")
|
||||
}
|
||||
|
||||
var err error
|
||||
cfg.defaultSource, err = parseDispatcherSrcCfg(globals, othersRaw)
|
||||
cfg.defaultSource, err = parseMsgPipelineSrcCfg(globals, othersRaw)
|
||||
return cfg, err
|
||||
} else if len(othersRaw) != 0 {
|
||||
return dispatcherCfg{}, config.NodeErr(&othersRaw[0], "can't put handling directives together with source rules, did you mean to put it into 'default_source' block or into all source blocks?")
|
||||
return msgpipelineCfg{}, config.NodeErr(&othersRaw[0], "can't put handling directives together with source rules, did you mean to put it into 'default_source' block or into all source blocks?")
|
||||
}
|
||||
|
||||
if len(defaultSrcRaw) == 0 {
|
||||
return dispatcherCfg{}, config.NodeErr(&nodes[0], "missing or empty default source block, use 'reject' to reject messages")
|
||||
return msgpipelineCfg{}, config.NodeErr(&nodes[0], "missing or empty default source block, use 'reject' to reject messages")
|
||||
}
|
||||
|
||||
var err error
|
||||
cfg.defaultSource, err = parseDispatcherSrcCfg(globals, defaultSrcRaw)
|
||||
cfg.defaultSource, err = parseMsgPipelineSrcCfg(globals, defaultSrcRaw)
|
||||
return cfg, err
|
||||
}
|
||||
|
||||
func parseDispatcherSrcCfg(globals map[string]interface{}, nodes []config.Node) (sourceBlock, error) {
|
||||
func parseMsgPipelineSrcCfg(globals map[string]interface{}, nodes []config.Node) (sourceBlock, error) {
|
||||
src := sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
}
|
||||
|
@ -153,18 +153,18 @@ func parseDispatcherSrcCfg(globals map[string]interface{}, nodes []config.Node)
|
|||
return sourceBlock{}, err
|
||||
}
|
||||
case "destination":
|
||||
rcptBlock, err := parseDispatcherRcptCfg(globals, node.Children)
|
||||
rcptBlock, err := parseMsgPipelineRcptCfg(globals, node.Children)
|
||||
if err != nil {
|
||||
return sourceBlock{}, err
|
||||
}
|
||||
|
||||
if len(node.Args) == 0 {
|
||||
return sourceBlock{}, config.NodeErr(&node, "expected at least one destination dispatch rule")
|
||||
return sourceBlock{}, config.NodeErr(&node, "expected at least one destination match rule")
|
||||
}
|
||||
|
||||
for _, rule := range node.Args {
|
||||
if !validDispatchRule(rule) {
|
||||
return sourceBlock{}, config.NodeErr(&node, "invalid destination dispatch rule: %v", rule)
|
||||
if !validMatchRule(rule) {
|
||||
return sourceBlock{}, config.NodeErr(&node, "invalid destination match rule: %v", rule)
|
||||
}
|
||||
|
||||
src.perRcpt[rule] = rcptBlock
|
||||
|
@ -185,7 +185,7 @@ func parseDispatcherSrcCfg(globals map[string]interface{}, nodes []config.Node)
|
|||
}
|
||||
|
||||
var err error
|
||||
src.defaultRcpt, err = parseDispatcherRcptCfg(globals, othersRaw)
|
||||
src.defaultRcpt, err = parseMsgPipelineRcptCfg(globals, othersRaw)
|
||||
return src, err
|
||||
} else if len(othersRaw) != 0 {
|
||||
return sourceBlock{}, config.NodeErr(&othersRaw[0], "can't put handling directives together with destination rules, did you mean to put it into 'default' block or into all recipient blocks?")
|
||||
|
@ -196,11 +196,11 @@ func parseDispatcherSrcCfg(globals map[string]interface{}, nodes []config.Node)
|
|||
}
|
||||
|
||||
var err error
|
||||
src.defaultRcpt, err = parseDispatcherRcptCfg(globals, defaultRcptRaw)
|
||||
src.defaultRcpt, err = parseMsgPipelineRcptCfg(globals, defaultRcptRaw)
|
||||
return src, err
|
||||
}
|
||||
|
||||
func parseDispatcherRcptCfg(globals map[string]interface{}, nodes []config.Node) (*rcptBlock, error) {
|
||||
func parseMsgPipelineRcptCfg(globals map[string]interface{}, nodes []config.Node) (*rcptBlock, error) {
|
||||
rcpt := rcptBlock{}
|
||||
for _, node := range nodes {
|
||||
switch node.Name {
|
||||
|
@ -337,6 +337,6 @@ func parseModifiersGroup(globals map[string]interface{}, nodes []config.Node) (m
|
|||
return modifiers, nil
|
||||
}
|
||||
|
||||
func validDispatchRule(rule string) bool {
|
||||
func validMatchRule(rule string) bool {
|
||||
return address.ValidDomain(rule) || address.Valid(rule)
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"reflect"
|
||||
|
@ -17,11 +17,11 @@ func policyError(code int) error {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcherCfg(t *testing.T) {
|
||||
func TestMsgPipelineCfg(t *testing.T) {
|
||||
cases := []struct {
|
||||
name string
|
||||
str string
|
||||
value dispatcherCfg
|
||||
value msgpipelineCfg
|
||||
fail bool
|
||||
}{
|
||||
{
|
||||
|
@ -43,7 +43,7 @@ func TestDispatcherCfg(t *testing.T) {
|
|||
reject 440
|
||||
}
|
||||
}`,
|
||||
value: dispatcherCfg{
|
||||
value: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"example.com": {
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -77,7 +77,7 @@ func TestDispatcherCfg(t *testing.T) {
|
|||
default_source {
|
||||
reject 420
|
||||
}`,
|
||||
value: dispatcherCfg{
|
||||
value: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"example.com": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -103,7 +103,7 @@ func TestDispatcherCfg(t *testing.T) {
|
|||
default_destination {
|
||||
reject 420
|
||||
}`,
|
||||
value: dispatcherCfg{
|
||||
value: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -208,7 +208,7 @@ func TestDispatcherCfg(t *testing.T) {
|
|||
case_ := case_
|
||||
t.Run(case_.name, func(t *testing.T) {
|
||||
cfg, _ := config.Read(strings.NewReader(case_.str), "literal")
|
||||
parsed, err := parseDispatcherRootCfg(nil, cfg)
|
||||
parsed, err := parseMsgPipelineRootCfg(nil, cfg)
|
||||
if err != nil && !case_.fail {
|
||||
t.Fatalf("unexpected parse error: %v", err)
|
||||
}
|
||||
|
@ -228,7 +228,7 @@ func TestDispatcherCfg(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcherCfg_GlobalChecks(t *testing.T) {
|
||||
func TestMsgPipelineCfg_GlobalChecks(t *testing.T) {
|
||||
str := `
|
||||
check {
|
||||
test_check
|
||||
|
@ -239,7 +239,7 @@ func TestDispatcherCfg_GlobalChecks(t *testing.T) {
|
|||
`
|
||||
|
||||
cfg, _ := config.Read(strings.NewReader(str), "literal")
|
||||
parsed, err := parseDispatcherRootCfg(nil, cfg)
|
||||
parsed, err := parseMsgPipelineRootCfg(nil, cfg)
|
||||
if err != nil {
|
||||
t.Fatalf("unexpected parse error: %v", err)
|
||||
}
|
||||
|
@ -249,7 +249,7 @@ func TestDispatcherCfg_GlobalChecks(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcherCfg_SourceChecks(t *testing.T) {
|
||||
func TestMsgPipelineCfg_SourceChecks(t *testing.T) {
|
||||
str := `
|
||||
source example.org {
|
||||
check {
|
||||
|
@ -264,7 +264,7 @@ func TestDispatcherCfg_SourceChecks(t *testing.T) {
|
|||
`
|
||||
|
||||
cfg, _ := config.Read(strings.NewReader(str), "literal")
|
||||
parsed, err := parseDispatcherRootCfg(nil, cfg)
|
||||
parsed, err := parseMsgPipelineRootCfg(nil, cfg)
|
||||
if err != nil {
|
||||
t.Fatalf("unexpected parse error: %v", err)
|
||||
}
|
||||
|
@ -274,7 +274,7 @@ func TestDispatcherCfg_SourceChecks(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcherCfg_RcptChecks(t *testing.T) {
|
||||
func TestMsgPipelineCfg_RcptChecks(t *testing.T) {
|
||||
str := `
|
||||
destination example.org {
|
||||
check {
|
||||
|
@ -289,7 +289,7 @@ func TestDispatcherCfg_RcptChecks(t *testing.T) {
|
|||
`
|
||||
|
||||
cfg, _ := config.Read(strings.NewReader(str), "literal")
|
||||
parsed, err := parseDispatcherRootCfg(nil, cfg)
|
||||
parsed, err := parseMsgPipelineRootCfg(nil, cfg)
|
||||
if err != nil {
|
||||
t.Fatalf("unexpected parse error: %v", err)
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
@ -9,7 +9,7 @@ import (
|
|||
"github.com/foxcpp/maddy/testutils"
|
||||
)
|
||||
|
||||
func TestDispatcher_SenderModifier(t *testing.T) {
|
||||
func TestMsgPipeline_SenderModifier(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
modifier := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -17,8 +17,8 @@ func TestDispatcher_SenderModifier(t *testing.T) {
|
|||
"sender@example.com": "sender2@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{modifier},
|
||||
},
|
||||
|
@ -30,7 +30,7 @@ func TestDispatcher_SenderModifier(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -46,7 +46,7 @@ func TestDispatcher_SenderModifier(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SenderModifier_Multiple(t *testing.T) {
|
||||
func TestMsgPipeline_SenderModifier_Multiple(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod1, mod2 := testutils.Modifier{
|
||||
InstName: "first_modifier",
|
||||
|
@ -59,8 +59,8 @@ func TestDispatcher_SenderModifier_Multiple(t *testing.T) {
|
|||
"sender2@example.com": "sender3@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod1, mod2},
|
||||
},
|
||||
|
@ -72,7 +72,7 @@ func TestDispatcher_SenderModifier_Multiple(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -88,7 +88,7 @@ func TestDispatcher_SenderModifier_Multiple(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SenderModifier_PreDispatch(t *testing.T) {
|
||||
func TestMsgPipeline_SenderModifier_PreDispatch(t *testing.T) {
|
||||
target := testutils.Target{InstName: "target"}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -96,8 +96,8 @@ func TestDispatcher_SenderModifier_PreDispatch(t *testing.T) {
|
|||
"sender@example.com": "sender@example.org",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod},
|
||||
},
|
||||
|
@ -111,7 +111,7 @@ func TestDispatcher_SenderModifier_PreDispatch(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -126,7 +126,7 @@ func TestDispatcher_SenderModifier_PreDispatch(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SenderModifier_PostDispatch(t *testing.T) {
|
||||
func TestMsgPipeline_SenderModifier_PostDispatch(t *testing.T) {
|
||||
target := testutils.Target{InstName: "target"}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -134,8 +134,8 @@ func TestDispatcher_SenderModifier_PostDispatch(t *testing.T) {
|
|||
"sender@example.org": "sender@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"example.org": {
|
||||
modifiers: modify.Group{
|
||||
|
@ -149,7 +149,7 @@ func TestDispatcher_SenderModifier_PostDispatch(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.org", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -164,7 +164,7 @@ func TestDispatcher_SenderModifier_PostDispatch(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SenderModifier_PerRcpt(t *testing.T) {
|
||||
func TestMsgPipeline_SenderModifier_PerRcpt(t *testing.T) {
|
||||
// Modifier below will be no-op due to implementation limitations.
|
||||
|
||||
comTarget, orgTarget := testutils.Target{InstName: "com_target"}, testutils.Target{InstName: "org_target"}
|
||||
|
@ -174,8 +174,8 @@ func TestDispatcher_SenderModifier_PerRcpt(t *testing.T) {
|
|||
"sender@example.com": "sender2@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -192,7 +192,7 @@ func TestDispatcher_SenderModifier_PerRcpt(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt@example.com", "rcpt@example.org"})
|
||||
|
@ -212,7 +212,7 @@ func TestDispatcher_SenderModifier_PerRcpt(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -221,8 +221,8 @@ func TestDispatcher_RcptModifier(t *testing.T) {
|
|||
"rcpt2@example.com": "rcpt2-alias@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod},
|
||||
},
|
||||
|
@ -234,7 +234,7 @@ func TestDispatcher_RcptModifier(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -250,7 +250,7 @@ func TestDispatcher_RcptModifier(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_OriginalRcpt(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_OriginalRcpt(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -259,8 +259,8 @@ func TestDispatcher_RcptModifier_OriginalRcpt(t *testing.T) {
|
|||
"rcpt2@example.com": "rcpt2-alias@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod},
|
||||
},
|
||||
|
@ -272,7 +272,7 @@ func TestDispatcher_RcptModifier_OriginalRcpt(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -296,7 +296,7 @@ func TestDispatcher_RcptModifier_OriginalRcpt(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_OriginalRcpt_Multiple(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_OriginalRcpt_Multiple(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod1, mod2 := testutils.Modifier{
|
||||
InstName: "first_modifier",
|
||||
|
@ -311,8 +311,8 @@ func TestDispatcher_RcptModifier_OriginalRcpt_Multiple(t *testing.T) {
|
|||
"rcpt2@example.com": "wtf@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod1},
|
||||
},
|
||||
|
@ -327,7 +327,7 @@ func TestDispatcher_RcptModifier_OriginalRcpt_Multiple(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -351,7 +351,7 @@ func TestDispatcher_RcptModifier_OriginalRcpt_Multiple(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_Multiple(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_Multiple(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod1, mod2 := testutils.Modifier{
|
||||
InstName: "first_modifier",
|
||||
|
@ -366,8 +366,8 @@ func TestDispatcher_RcptModifier_Multiple(t *testing.T) {
|
|||
"rcpt2@example.com": "wtf@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod1, mod2},
|
||||
},
|
||||
|
@ -379,7 +379,7 @@ func TestDispatcher_RcptModifier_Multiple(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -395,7 +395,7 @@ func TestDispatcher_RcptModifier_Multiple(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_PreDispatch(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_PreDispatch(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod1, mod2 := testutils.Modifier{
|
||||
InstName: "first_modifier",
|
||||
|
@ -410,8 +410,8 @@ func TestDispatcher_RcptModifier_PreDispatch(t *testing.T) {
|
|||
"rcpt2@example.com": "wtf@example.com",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{
|
||||
Modifiers: []module.Modifier{mod1},
|
||||
},
|
||||
|
@ -431,7 +431,7 @@ func TestDispatcher_RcptModifier_PreDispatch(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -447,7 +447,7 @@ func TestDispatcher_RcptModifier_PreDispatch(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_PostDispatch(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_PostDispatch(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -456,8 +456,8 @@ func TestDispatcher_RcptModifier_PostDispatch(t *testing.T) {
|
|||
"rcpt2@example.com": "rcpt2@example.org",
|
||||
},
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -476,7 +476,7 @@ func TestDispatcher_RcptModifier_PostDispatch(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -492,7 +492,7 @@ func TestDispatcher_RcptModifier_PostDispatch(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_GlobalModifier_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_GlobalModifier_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -501,8 +501,8 @@ func TestDispatcher_GlobalModifier_Errors(t *testing.T) {
|
|||
RcptToErr: errors.New("3"),
|
||||
BodyErr: errors.New("4"),
|
||||
}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
globalModifiers: modify.Group{Modifiers: []module.Modifier{&mod}},
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -511,7 +511,7 @@ func TestDispatcher_GlobalModifier_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
||||
|
@ -559,7 +559,7 @@ func TestDispatcher_GlobalModifier_Errors(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_SourceModifier_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_SourceModifier_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -570,8 +570,8 @@ func TestDispatcher_SourceModifier_Errors(t *testing.T) {
|
|||
}
|
||||
// Added to make sure it is freed properly too.
|
||||
globalMod := testutils.Modifier{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
globalModifiers: modify.Group{Modifiers: []module.Modifier{&globalMod}},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -581,7 +581,7 @@ func TestDispatcher_SourceModifier_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
||||
|
@ -630,7 +630,7 @@ func TestDispatcher_SourceModifier_Errors(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_RcptModifier_Errors(t *testing.T) {
|
||||
func TestMsgPipeline_RcptModifier_Errors(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
mod := testutils.Modifier{
|
||||
InstName: "test_modifier",
|
||||
|
@ -641,8 +641,8 @@ func TestDispatcher_RcptModifier_Errors(t *testing.T) {
|
|||
globalMod := testutils.Modifier{}
|
||||
sourceMod := testutils.Modifier{}
|
||||
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
globalModifiers: modify.Group{Modifiers: []module.Modifier{&globalMod}},
|
||||
defaultSource: sourceBlock{
|
||||
|
@ -653,7 +653,7 @@ func TestDispatcher_RcptModifier_Errors(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
t.Run("init err", func(t *testing.T) {
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"encoding/hex"
|
||||
|
@ -7,7 +7,7 @@ import (
|
|||
|
||||
// GenerateMsgID generates a string usable as MsgID field in module.MsgMeta.
|
||||
//
|
||||
// TODO: Find a better place for this function. 'dispatcher' package seems
|
||||
// TODO: Find a better place for this function. 'msgpipeline' package seems
|
||||
// irrelevant.
|
||||
func GenerateMsgID() (string, error) {
|
||||
rawID := make([]byte, 32)
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"strings"
|
||||
|
@ -14,15 +14,15 @@ import (
|
|||
"github.com/foxcpp/maddy/target"
|
||||
)
|
||||
|
||||
// Dispatcher is a object that is responsible for selecting delivery targets
|
||||
// MsgPipeline is a object that is responsible for selecting delivery targets
|
||||
// for the message and running necessary checks and modifier.
|
||||
//
|
||||
// It implements module.DeliveryTarget.
|
||||
//
|
||||
// It is not a "module object" and is intended to be used as part of message
|
||||
// source (Submission, SMTP, JMAP modules) implementation.
|
||||
type Dispatcher struct {
|
||||
dispatcherCfg
|
||||
type MsgPipeline struct {
|
||||
msgpipelineCfg
|
||||
Hostname string
|
||||
|
||||
Log log.Logger
|
||||
|
@ -43,10 +43,10 @@ type rcptBlock struct {
|
|||
targets []module.DeliveryTarget
|
||||
}
|
||||
|
||||
func NewDispatcher(globals map[string]interface{}, cfg []config.Node) (*Dispatcher, error) {
|
||||
parsedCfg, err := parseDispatcherRootCfg(globals, cfg)
|
||||
return &Dispatcher{
|
||||
dispatcherCfg: parsedCfg,
|
||||
func New(globals map[string]interface{}, cfg []config.Node) (*MsgPipeline, error) {
|
||||
parsedCfg, err := parseMsgPipelineRootCfg(globals, cfg)
|
||||
return &MsgPipeline{
|
||||
msgpipelineCfg: parsedCfg,
|
||||
}, err
|
||||
}
|
||||
|
||||
|
@ -54,10 +54,10 @@ func NewDispatcher(globals map[string]interface{}, cfg []config.Node) (*Dispatch
|
|||
// and selects source block from config to use for handling.
|
||||
//
|
||||
// Returned module.Delivery implements PartialDelivery. If underlying target doesn't
|
||||
// support it, dispatcher will copy the returned error for all recipients handled
|
||||
// support it, msgpipeline will copy the returned error for all recipients handled
|
||||
// by target.
|
||||
func (d *Dispatcher) Start(msgMeta *module.MsgMetadata, mailFrom string) (module.Delivery, error) {
|
||||
dd := dispatcherDelivery{
|
||||
func (d *MsgPipeline) Start(msgMeta *module.MsgMetadata, mailFrom string) (module.Delivery, error) {
|
||||
dd := msgpipelineDelivery{
|
||||
d: d,
|
||||
rcptModifiersState: make(map[*rcptBlock]module.ModifierState),
|
||||
deliveries: make(map[module.DeliveryTarget]*delivery),
|
||||
|
@ -78,7 +78,7 @@ func (d *Dispatcher) Start(msgMeta *module.MsgMetadata, mailFrom string) (module
|
|||
return &dd, nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) start(msgMeta *module.MsgMetadata, mailFrom string) error {
|
||||
func (dd *msgpipelineDelivery) start(msgMeta *module.MsgMetadata, mailFrom string) error {
|
||||
var err error
|
||||
|
||||
if err := dd.checkRunner.checkConnSender(dd.d.globalChecks, mailFrom); err != nil {
|
||||
|
@ -117,7 +117,7 @@ func (dd *dispatcherDelivery) start(msgMeta *module.MsgMetadata, mailFrom string
|
|||
return nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) initRunGlobalModifiers(msgMeta *module.MsgMetadata, mailFrom string) (string, error) {
|
||||
func (dd *msgpipelineDelivery) initRunGlobalModifiers(msgMeta *module.MsgMetadata, mailFrom string) (string, error) {
|
||||
globalModifiersState, err := dd.d.globalModifiers.ModStateForMsg(msgMeta)
|
||||
if err != nil {
|
||||
return "", err
|
||||
|
@ -131,7 +131,7 @@ func (dd *dispatcherDelivery) initRunGlobalModifiers(msgMeta *module.MsgMetadata
|
|||
return mailFrom, nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) srcBlockForAddr(mailFrom string) (sourceBlock, error) {
|
||||
func (dd *msgpipelineDelivery) srcBlockForAddr(mailFrom string) (sourceBlock, error) {
|
||||
// First try to match against complete address.
|
||||
srcBlock, ok := dd.d.perSource[strings.ToLower(mailFrom)]
|
||||
if !ok {
|
||||
|
@ -169,8 +169,8 @@ type delivery struct {
|
|||
recipients []string
|
||||
}
|
||||
|
||||
type dispatcherDelivery struct {
|
||||
d *Dispatcher
|
||||
type msgpipelineDelivery struct {
|
||||
d *MsgPipeline
|
||||
|
||||
globalModifiersState module.ModifierState
|
||||
sourceModifiersState module.ModifierState
|
||||
|
@ -186,7 +186,7 @@ type dispatcherDelivery struct {
|
|||
checkRunner *checkRunner
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) AddRcpt(to string) error {
|
||||
func (dd *msgpipelineDelivery) AddRcpt(to string) error {
|
||||
if err := dd.checkRunner.checkRcpt(dd.d.globalChecks, to); err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -257,7 +257,7 @@ func (dd *dispatcherDelivery) AddRcpt(to string) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) Body(header textproto.Header, body buffer.Buffer) error {
|
||||
func (dd *msgpipelineDelivery) Body(header textproto.Header, body buffer.Buffer) error {
|
||||
if err := dd.checkRunner.checkBody(dd.d.globalChecks, header, body); err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -310,7 +310,7 @@ func (sc statusCollector) SetStatus(rcptTo string, err error) {
|
|||
sc.wrapped.SetStatus(rcptTo, err)
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) BodyNonAtomic(c module.StatusCollector, header textproto.Header, body buffer.Buffer) {
|
||||
func (dd *msgpipelineDelivery) BodyNonAtomic(c module.StatusCollector, header textproto.Header, body buffer.Buffer) {
|
||||
setStatusAll := func(err error) {
|
||||
for _, delivery := range dd.deliveries {
|
||||
for _, rcpt := range delivery.recipients {
|
||||
|
@ -359,7 +359,7 @@ func (dd *dispatcherDelivery) BodyNonAtomic(c module.StatusCollector, header tex
|
|||
}
|
||||
}
|
||||
|
||||
func (dd dispatcherDelivery) Commit() error {
|
||||
func (dd msgpipelineDelivery) Commit() error {
|
||||
dd.close()
|
||||
|
||||
for _, delivery := range dd.deliveries {
|
||||
|
@ -373,7 +373,7 @@ func (dd dispatcherDelivery) Commit() error {
|
|||
return nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) close() {
|
||||
func (dd *msgpipelineDelivery) close() {
|
||||
dd.checkRunner.close()
|
||||
|
||||
if dd.globalModifiersState != nil {
|
||||
|
@ -387,7 +387,7 @@ func (dd *dispatcherDelivery) close() {
|
|||
}
|
||||
}
|
||||
|
||||
func (dd dispatcherDelivery) Abort() error {
|
||||
func (dd msgpipelineDelivery) Abort() error {
|
||||
dd.close()
|
||||
|
||||
var lastErr error
|
||||
|
@ -403,7 +403,7 @@ func (dd dispatcherDelivery) Abort() error {
|
|||
return lastErr
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) rcptBlockForAddr(rcptTo string) (*rcptBlock, error) {
|
||||
func (dd *msgpipelineDelivery) rcptBlockForAddr(rcptTo string) (*rcptBlock, error) {
|
||||
// First try to match against complete address.
|
||||
rcptBlock, ok := dd.sourceBlock.perRcpt[strings.ToLower(rcptTo)]
|
||||
if !ok {
|
||||
|
@ -431,7 +431,7 @@ func (dd *dispatcherDelivery) rcptBlockForAddr(rcptTo string) (*rcptBlock, error
|
|||
return rcptBlock, nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) getRcptModifiers(rcptBlock *rcptBlock, rcptTo string) (module.ModifierState, error) {
|
||||
func (dd *msgpipelineDelivery) getRcptModifiers(rcptBlock *rcptBlock, rcptTo string) (module.ModifierState, error) {
|
||||
rcptModifiersState, ok := dd.rcptModifiersState[rcptBlock]
|
||||
if ok {
|
||||
return rcptModifiersState, nil
|
||||
|
@ -453,7 +453,7 @@ func (dd *dispatcherDelivery) getRcptModifiers(rcptBlock *rcptBlock, rcptTo stri
|
|||
return rcptModifiersState, nil
|
||||
}
|
||||
|
||||
func (dd *dispatcherDelivery) getDelivery(tgt module.DeliveryTarget) (*delivery, error) {
|
||||
func (dd *msgpipelineDelivery) getDelivery(tgt module.DeliveryTarget) (*delivery, error) {
|
||||
delivery_, ok := dd.deliveries[tgt]
|
||||
if ok {
|
||||
return delivery_, nil
|
|
@ -1,4 +1,4 @@
|
|||
package dispatcher
|
||||
package msgpipeline
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
@ -10,10 +10,10 @@ import (
|
|||
"github.com/foxcpp/maddy/testutils"
|
||||
)
|
||||
|
||||
func TestDispatcher_AllToTarget(t *testing.T) {
|
||||
func TestMsgPipeline_AllToTarget(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -22,7 +22,7 @@ func TestDispatcher_AllToTarget(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -34,10 +34,10 @@ func TestDispatcher_AllToTarget(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 0, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PerSourceDomainSplit(t *testing.T) {
|
||||
func TestMsgPipeline_PerSourceDomainSplit(t *testing.T) {
|
||||
orgTarget, comTarget := testutils.Target{InstName: "orgTarget"}, testutils.Target{InstName: "comTarget"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"example.com": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -54,7 +54,7 @@ func TestDispatcher_PerSourceDomainSplit(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -71,10 +71,10 @@ func TestDispatcher_PerSourceDomainSplit(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &orgTarget, 0, "sender@example.org", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_EmptyMAILFROM(t *testing.T) {
|
||||
func TestMsgPipeline_EmptyMAILFROM(t *testing.T) {
|
||||
target := testutils.Target{InstName: "target"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -83,7 +83,7 @@ func TestDispatcher_EmptyMAILFROM(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -94,10 +94,10 @@ func TestDispatcher_EmptyMAILFROM(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 0, "", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_EmptyMAILFROM_ExplicitDest(t *testing.T) {
|
||||
func TestMsgPipeline_EmptyMAILFROM_ExplicitDest(t *testing.T) {
|
||||
target := testutils.Target{InstName: "target"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -108,7 +108,7 @@ func TestDispatcher_EmptyMAILFROM_ExplicitDest(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
|
@ -119,10 +119,10 @@ func TestDispatcher_EmptyMAILFROM_ExplicitDest(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 0, "", []string{"rcpt1@example.com", "rcpt2@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PerRcptAddrSplit(t *testing.T) {
|
||||
func TestMsgPipeline_PerRcptAddrSplit(t *testing.T) {
|
||||
target1, target2 := testutils.Target{InstName: "target1"}, testutils.Target{InstName: "target2"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"sender1@example.com": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -139,7 +139,7 @@ func TestDispatcher_PerRcptAddrSplit(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender1@example.com", []string{"rcpt@example.com"})
|
||||
|
@ -156,10 +156,10 @@ func TestDispatcher_PerRcptAddrSplit(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target2, 0, "sender2@example.com", []string{"rcpt@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PerRcptDomainSplit(t *testing.T) {
|
||||
func TestMsgPipeline_PerRcptDomainSplit(t *testing.T) {
|
||||
target1, target2 := testutils.Target{InstName: "target1"}, testutils.Target{InstName: "target2"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -175,7 +175,7 @@ func TestDispatcher_PerRcptDomainSplit(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"rcpt1@example.com", "rcpt2@example.org"})
|
||||
|
@ -194,10 +194,10 @@ func TestDispatcher_PerRcptDomainSplit(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target2, 1, "sender@example.com", []string{"rcpt1@example.org"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PerSourceAddrAndDomainSplit(t *testing.T) {
|
||||
func TestMsgPipeline_PerSourceAddrAndDomainSplit(t *testing.T) {
|
||||
target1, target2 := testutils.Target{InstName: "target1"}, testutils.Target{InstName: "target2"}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"sender1@example.com": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -213,7 +213,7 @@ func TestDispatcher_PerSourceAddrAndDomainSplit(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("default src block used")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender1@example.com", []string{"rcpt@example.com"})
|
||||
|
@ -230,10 +230,10 @@ func TestDispatcher_PerSourceAddrAndDomainSplit(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target2, 0, "sender2@example.com", []string{"rcpt@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PerSourceReject(t *testing.T) {
|
||||
func TestMsgPipeline_PerSourceReject(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"sender1@example.com": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -247,7 +247,7 @@ func TestDispatcher_PerSourceReject(t *testing.T) {
|
|||
},
|
||||
defaultSource: sourceBlock{rejectErr: errors.New("go away")},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender1@example.com", []string{"rcpt@example.com"})
|
||||
|
@ -263,10 +263,10 @@ func TestDispatcher_PerSourceReject(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_PerRcptReject(t *testing.T) {
|
||||
func TestMsgPipeline_PerRcptReject(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -282,7 +282,7 @@ func TestDispatcher_PerRcptReject(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
delivery, err := d.Start(&module.MsgMetadata{ID: "testing"}, "sender@example.com")
|
||||
|
@ -305,10 +305,10 @@ func TestDispatcher_PerRcptReject(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_PostmasterRcpt(t *testing.T) {
|
||||
func TestMsgPipeline_PostmasterRcpt(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -324,7 +324,7 @@ func TestDispatcher_PostmasterRcpt(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "disappointed-user@example.com", []string{"postmaster"})
|
||||
|
@ -334,10 +334,10 @@ func TestDispatcher_PostmasterRcpt(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 0, "disappointed-user@example.com", []string{"postmaster"})
|
||||
}
|
||||
|
||||
func TestDispatcher_PostmasterSrc(t *testing.T) {
|
||||
func TestMsgPipeline_PostmasterSrc(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"postmaster": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -353,7 +353,7 @@ func TestDispatcher_PostmasterSrc(t *testing.T) {
|
|||
rejectErr: errors.New("go away"),
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "postmaster", []string{"disappointed-user@example.com"})
|
||||
|
@ -363,10 +363,10 @@ func TestDispatcher_PostmasterSrc(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 0, "postmaster", []string{"disappointed-user@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_CaseInsensetiveMatch_Src(t *testing.T) {
|
||||
func TestMsgPipeline_CaseInsensetiveMatch_Src(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{
|
||||
"postmaster": {
|
||||
perRcpt: map[string]*rcptBlock{},
|
||||
|
@ -391,7 +391,7 @@ func TestDispatcher_CaseInsensetiveMatch_Src(t *testing.T) {
|
|||
rejectErr: errors.New("go away"),
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "POSTMastER", []string{"disappointed-user@example.com"})
|
||||
|
@ -405,10 +405,10 @@ func TestDispatcher_CaseInsensetiveMatch_Src(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 2, "sender@exAMPle.com", []string{"disappointed-user@example.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_CaseInsensetiveMatch_Rcpt(t *testing.T) {
|
||||
func TestMsgPipeline_CaseInsensetiveMatch_Rcpt(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -424,7 +424,7 @@ func TestDispatcher_CaseInsensetiveMatch_Rcpt(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"POSTMastER"})
|
||||
|
@ -438,10 +438,10 @@ func TestDispatcher_CaseInsensetiveMatch_Rcpt(t *testing.T) {
|
|||
testutils.CheckTestMessage(t, &target, 2, "sender@example.com", []string{"sender@exAMPle.com"})
|
||||
}
|
||||
|
||||
func TestDispatcher_MalformedSource(t *testing.T) {
|
||||
func TestMsgPipeline_MalformedSource(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -457,10 +457,10 @@ func TestDispatcher_MalformedSource(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
// Simple checks for violations that can make dispatcher misbehave.
|
||||
// Simple checks for violations that can make msgpipeline misbehave.
|
||||
for _, addr := range []string{"not_postmaster_but_no_at_sign", "@no_mailbox", "no_domain@", "that@is@definiely@broken"} {
|
||||
_, err := d.Start(&module.MsgMetadata{ID: "testing"}, addr)
|
||||
if err == nil {
|
||||
|
@ -469,10 +469,10 @@ func TestDispatcher_MalformedSource(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestDispatcher_TwoRcptToOneTarget(t *testing.T) {
|
||||
func TestMsgPipeline_TwoRcptToOneTarget(t *testing.T) {
|
||||
target := testutils.Target{}
|
||||
d := Dispatcher{
|
||||
dispatcherCfg: dispatcherCfg{
|
||||
d := MsgPipeline{
|
||||
msgpipelineCfg: msgpipelineCfg{
|
||||
perSource: map[string]sourceBlock{},
|
||||
defaultSource: sourceBlock{
|
||||
perRcpt: map[string]*rcptBlock{
|
||||
|
@ -485,7 +485,7 @@ func TestDispatcher_TwoRcptToOneTarget(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
Log: testutils.Logger(t, "dispatcher"),
|
||||
Log: testutils.Logger(t, "msgpipeline"),
|
||||
}
|
||||
|
||||
testutils.DoTestDelivery(t, &d, "sender@example.com", []string{"recipient@example.com", "recipient@example.org"})
|
|
@ -59,11 +59,11 @@ import (
|
|||
"github.com/foxcpp/maddy/buffer"
|
||||
"github.com/foxcpp/maddy/config"
|
||||
modconfig "github.com/foxcpp/maddy/config/module"
|
||||
"github.com/foxcpp/maddy/dispatcher"
|
||||
"github.com/foxcpp/maddy/dsn"
|
||||
"github.com/foxcpp/maddy/exterrors"
|
||||
"github.com/foxcpp/maddy/log"
|
||||
"github.com/foxcpp/maddy/module"
|
||||
"github.com/foxcpp/maddy/msgpipeline"
|
||||
"github.com/foxcpp/maddy/target"
|
||||
)
|
||||
|
||||
|
@ -110,7 +110,7 @@ type Queue struct {
|
|||
autogenMsgDomain string
|
||||
wheel *TimeWheel
|
||||
|
||||
dsnDispatcher *dispatcher.Dispatcher
|
||||
dsnPipeline *msgpipeline.MsgPipeline
|
||||
|
||||
// Retry delay is calculated using the following formula:
|
||||
// initialRetryTime * retryTimeScale ^ (TriesCount - 1)
|
||||
|
@ -195,19 +195,19 @@ func (q *Queue) Init(cfg *config.Map) error {
|
|||
cfg.String("hostname", true, true, "", &q.hostname)
|
||||
cfg.String("autogenerated_msg_domain", true, false, "", &q.autogenMsgDomain)
|
||||
cfg.Custom("bounce", false, false, nil, func(m *config.Map, node *config.Node) (interface{}, error) {
|
||||
return dispatcher.NewDispatcher(m.Globals, node.Children)
|
||||
}, &q.dsnDispatcher)
|
||||
return msgpipeline.New(m.Globals, node.Children)
|
||||
}, &q.dsnPipeline)
|
||||
if _, err := cfg.Process(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if q.dsnDispatcher != nil {
|
||||
if q.dsnPipeline != nil {
|
||||
if q.autogenMsgDomain == "" {
|
||||
return errors.New("queue: autogenerated_msg_domain is required if bounce {} is specified")
|
||||
}
|
||||
|
||||
q.dsnDispatcher.Hostname = q.hostname
|
||||
q.dsnDispatcher.Log = log.Logger{Name: "queue/dispatcher", Debug: q.Log.Debug}
|
||||
q.dsnPipeline.Hostname = q.hostname
|
||||
q.dsnPipeline.Log = log.Logger{Name: "queue/msgpipeline", Debug: q.Log.Debug}
|
||||
}
|
||||
if q.location == "" && q.name == "" {
|
||||
return errors.New("queue: need explicit location directive or inline argument if defined inline")
|
||||
|
@ -347,7 +347,7 @@ func (q *Queue) deliver(meta *QueueMetadata, header textproto.Header, body buffe
|
|||
|
||||
deliveryTarget := q.Target
|
||||
if meta.DSN {
|
||||
deliveryTarget = q.dsnDispatcher
|
||||
deliveryTarget = q.dsnPipeline
|
||||
}
|
||||
|
||||
msgMeta := meta.MsgMeta.DeepCopy()
|
||||
|
@ -739,12 +739,12 @@ func (q *Queue) Name() string {
|
|||
}
|
||||
|
||||
func (q *Queue) emitDSN(meta *QueueMetadata, header textproto.Header) {
|
||||
// If, apparently, we have no DSN dispatcher configured - do nothing.
|
||||
if q.dsnDispatcher == nil {
|
||||
// If, apparently, we have no DSN msgpipeline configured - do nothing.
|
||||
if q.dsnPipeline == nil {
|
||||
return
|
||||
}
|
||||
|
||||
dsnID, err := dispatcher.GenerateMsgID()
|
||||
dsnID, err := msgpipeline.GenerateMsgID()
|
||||
if err != nil {
|
||||
q.Log.Printf("rand.Rand error: %v", err)
|
||||
return
|
||||
|
|
|
@ -461,7 +461,7 @@ func TestQueueDelivery_SerializationRoundtrip(t *testing.T) {
|
|||
defer cleanQueue(t, q)
|
||||
|
||||
// This is the most tricky test because it is racy and I have no idea what can be done to avoid it.
|
||||
// It relies on us calling Close before queue dispatcher decides to retry delivery.
|
||||
// It relies on us calling Close before queue msgpipeline decides to retry delivery.
|
||||
// Hence retry delay is increased from 0ms used in other tests to make it reliable.
|
||||
q.initialRetryTime = 1 * time.Second
|
||||
|
||||
|
@ -512,7 +512,7 @@ func TestQueueDelivery_DeserlizationCleanUp(t *testing.T) {
|
|||
defer cleanQueue(t, q)
|
||||
|
||||
// This is the most tricky test because it is racy and I have no idea what can be done to avoid it.
|
||||
// It relies on us calling Close before queue dispatcher decides to retry delivery.
|
||||
// It relies on us calling Close before queue msgpipeline decides to retry delivery.
|
||||
// Hence retry delay is increased from 0ms used in other tests to make it reliable.
|
||||
q.initialRetryTime = 1 * time.Second
|
||||
|
||||
|
|
|
@ -39,7 +39,7 @@ type Target struct {
|
|||
}
|
||||
|
||||
/*
|
||||
module.Module is implemented with dummy functions for logging done by Dispatcher code.
|
||||
module.Module is implemented with dummy functions for logging done by MsgPipeline code.
|
||||
*/
|
||||
|
||||
func (dt Target) Init(*config.Map) error {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue