feat: restrict smtp sender address (#3637)

* fix: check if sender address is custom domain

* fix: check if sender address is custom domain

* fix: check if sender address is custom domain

Co-authored-by: Livio Amstutz <livio.a@gmail.com>
This commit is contained in:
Fabi
2022-05-16 16:08:47 +02:00
committed by GitHub
parent 40de8d5b3b
commit 5c0f527a49
39 changed files with 510 additions and 153 deletions

View File

@@ -23,8 +23,9 @@ type DomainPolicy struct {
ResourceOwner string
State domain.PolicyState
UserLoginMustBeDomain bool
ValidateOrgDomains bool
UserLoginMustBeDomain bool
ValidateOrgDomains bool
SMTPSenderAddressMatchesInstanceDomain bool
IsDefault bool
}
@@ -65,6 +66,10 @@ var (
name: projection.DomainPolicyValidateOrgDomainsCol,
table: domainPolicyTable,
}
DomainPolicyColSMTPSenderAddressMatchesInstanceDomain = Column{
name: projection.DomainPolicySMTPSenderAddressMatchesInstanceDomainCol,
table: domainPolicyTable,
}
DomainPolicyColIsDefault = Column{
name: projection.DomainPolicyIsDefaultCol,
table: domainPolicyTable,
@@ -126,6 +131,7 @@ func prepareDomainPolicyQuery() (sq.SelectBuilder, func(*sql.Row) (*DomainPolicy
DomainPolicyColResourceOwner.identifier(),
DomainPolicyColUserLoginMustBeDomain.identifier(),
DomainPolicyColValidateOrgDomains.identifier(),
DomainPolicyColSMTPSenderAddressMatchesInstanceDomain.identifier(),
DomainPolicyColIsDefault.identifier(),
DomainPolicyColState.identifier(),
).
@@ -140,6 +146,7 @@ func prepareDomainPolicyQuery() (sq.SelectBuilder, func(*sql.Row) (*DomainPolicy
&policy.ResourceOwner,
&policy.UserLoginMustBeDomain,
&policy.ValidateOrgDomains,
&policy.SMTPSenderAddressMatchesInstanceDomain,
&policy.IsDefault,
&policy.State,
)

View File

@@ -35,6 +35,7 @@ func Test_DomainPolicyPrepares(t *testing.T) {
` projections.domain_policies.resource_owner,`+
` projections.domain_policies.user_login_must_be_domain,`+
` projections.domain_policies.validate_org_domains,`+
` projections.domain_policies.smtp_sender_address_matches_instance_domain,`+
` projections.domain_policies.is_default,`+
` projections.domain_policies.state`+
` FROM projections.domain_policies`),
@@ -62,6 +63,7 @@ func Test_DomainPolicyPrepares(t *testing.T) {
` projections.domain_policies.resource_owner,`+
` projections.domain_policies.user_login_must_be_domain,`+
` projections.domain_policies.validate_org_domains,`+
` projections.domain_policies.smtp_sender_address_matches_instance_domain,`+
` projections.domain_policies.is_default,`+
` projections.domain_policies.state`+
` FROM projections.domain_policies`),
@@ -73,6 +75,7 @@ func Test_DomainPolicyPrepares(t *testing.T) {
"resource_owner",
"user_login_must_be_domain",
"validate_org_domains",
"smtp_sender_address_matches_instance_domain",
"is_default",
"state",
},
@@ -85,20 +88,22 @@ func Test_DomainPolicyPrepares(t *testing.T) {
true,
true,
true,
true,
domain.PolicyStateActive,
},
),
},
object: &DomainPolicy{
ID: "pol-id",
CreationDate: testNow,
ChangeDate: testNow,
Sequence: 20211109,
ResourceOwner: "ro",
State: domain.PolicyStateActive,
UserLoginMustBeDomain: true,
ValidateOrgDomains: true,
IsDefault: true,
ID: "pol-id",
CreationDate: testNow,
ChangeDate: testNow,
Sequence: 20211109,
ResourceOwner: "ro",
State: domain.PolicyStateActive,
UserLoginMustBeDomain: true,
ValidateOrgDomains: true,
SMTPSenderAddressMatchesInstanceDomain: true,
IsDefault: true,
},
},
{
@@ -113,6 +118,7 @@ func Test_DomainPolicyPrepares(t *testing.T) {
` projections.domain_policies.resource_owner,`+
` projections.domain_policies.user_login_must_be_domain,`+
` projections.domain_policies.validate_org_domains,`+
` projections.domain_policies.smtp_sender_address_matches_instance_domain,`+
` projections.domain_policies.is_default,`+
` projections.domain_policies.state`+
` FROM projections.domain_policies`),

View File

@@ -16,16 +16,17 @@ import (
const (
DomainPolicyTable = "projections.domain_policies"
DomainPolicyIDCol = "id"
DomainPolicyCreationDateCol = "creation_date"
DomainPolicyChangeDateCol = "change_date"
DomainPolicySequenceCol = "sequence"
DomainPolicyStateCol = "state"
DomainPolicyUserLoginMustBeDomainCol = "user_login_must_be_domain"
DomainPolicyValidateOrgDomainsCol = "validate_org_domains"
DomainPolicyIsDefaultCol = "is_default"
DomainPolicyResourceOwnerCol = "resource_owner"
DomainPolicyInstanceIDCol = "instance_id"
DomainPolicyIDCol = "id"
DomainPolicyCreationDateCol = "creation_date"
DomainPolicyChangeDateCol = "change_date"
DomainPolicySequenceCol = "sequence"
DomainPolicyStateCol = "state"
DomainPolicyUserLoginMustBeDomainCol = "user_login_must_be_domain"
DomainPolicyValidateOrgDomainsCol = "validate_org_domains"
DomainPolicySMTPSenderAddressMatchesInstanceDomainCol = "smtp_sender_address_matches_instance_domain"
DomainPolicyIsDefaultCol = "is_default"
DomainPolicyResourceOwnerCol = "resource_owner"
DomainPolicyInstanceIDCol = "instance_id"
)
type DomainPolicyProjection struct {
@@ -45,6 +46,7 @@ func NewDomainPolicyProjection(ctx context.Context, config crdb.StatementHandler
crdb.NewColumn(DomainPolicyStateCol, crdb.ColumnTypeEnum),
crdb.NewColumn(DomainPolicyUserLoginMustBeDomainCol, crdb.ColumnTypeBool),
crdb.NewColumn(DomainPolicyValidateOrgDomainsCol, crdb.ColumnTypeBool),
crdb.NewColumn(DomainPolicySMTPSenderAddressMatchesInstanceDomainCol, crdb.ColumnTypeBool),
crdb.NewColumn(DomainPolicyIsDefaultCol, crdb.ColumnTypeBool, crdb.Default(false)),
crdb.NewColumn(DomainPolicyResourceOwnerCol, crdb.ColumnTypeText),
crdb.NewColumn(DomainPolicyInstanceIDCol, crdb.ColumnTypeText),
@@ -114,6 +116,7 @@ func (p *DomainPolicyProjection) reduceAdded(event eventstore.Event) (*handler.S
handler.NewCol(DomainPolicyStateCol, domain.PolicyStateActive),
handler.NewCol(DomainPolicyUserLoginMustBeDomainCol, policyEvent.UserLoginMustBeDomain),
handler.NewCol(DomainPolicyValidateOrgDomainsCol, policyEvent.ValidateOrgDomains),
handler.NewCol(DomainPolicySMTPSenderAddressMatchesInstanceDomainCol, policyEvent.SMTPSenderAddressMatchesInstanceDomain),
handler.NewCol(DomainPolicyIsDefaultCol, isDefault),
handler.NewCol(DomainPolicyResourceOwnerCol, policyEvent.Aggregate().ResourceOwner),
handler.NewCol(DomainPolicyInstanceIDCol, policyEvent.Aggregate().InstanceID),
@@ -140,6 +143,9 @@ func (p *DomainPolicyProjection) reduceChanged(event eventstore.Event) (*handler
if policyEvent.ValidateOrgDomains != nil {
cols = append(cols, handler.NewCol(DomainPolicyValidateOrgDomainsCol, *policyEvent.ValidateOrgDomains))
}
if policyEvent.SMTPSenderAddressMatchesInstanceDomain != nil {
cols = append(cols, handler.NewCol(DomainPolicySMTPSenderAddressMatchesInstanceDomainCol, *policyEvent.SMTPSenderAddressMatchesInstanceDomain))
}
return crdb.NewUpdateStatement(
&policyEvent,
cols,

View File

@@ -30,7 +30,8 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
org.AggregateType,
[]byte(`{
"userLoginMustBeDomain": true,
"validateOrgDomains": true
"validateOrgDomains": true,
"smtpSenderAddressMatchesInstanceDomain": true
}`),
), org.DomainPolicyAddedEventMapper),
},
@@ -43,7 +44,7 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
executer: &testExecuter{
executions: []execution{
{
expectedStmt: "INSERT INTO projections.domain_policies (creation_date, change_date, sequence, id, state, user_login_must_be_domain, validate_org_domains, is_default, resource_owner, instance_id) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)",
expectedStmt: "INSERT INTO projections.domain_policies (creation_date, change_date, sequence, id, state, user_login_must_be_domain, validate_org_domains, smtp_sender_address_matches_instance_domain, is_default, resource_owner, instance_id) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11)",
expectedArgs: []interface{}{
anyArg{},
anyArg{},
@@ -52,6 +53,7 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
domain.PolicyStateActive,
true,
true,
true,
false,
"ro-id",
"instance-id",
@@ -70,7 +72,8 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
org.AggregateType,
[]byte(`{
"userLoginMustBeDomain": true,
"validateOrgDomains": true
"validateOrgDomains": true,
"smtpSenderAddressMatchesInstanceDomain": true
}`),
), org.DomainPolicyChangedEventMapper),
},
@@ -82,12 +85,13 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
executer: &testExecuter{
executions: []execution{
{
expectedStmt: "UPDATE projections.domain_policies SET (change_date, sequence, user_login_must_be_domain, validate_org_domains) = ($1, $2, $3, $4) WHERE (id = $5)",
expectedStmt: "UPDATE projections.domain_policies SET (change_date, sequence, user_login_must_be_domain, validate_org_domains, smtp_sender_address_matches_instance_domain) = ($1, $2, $3, $4, $5) WHERE (id = $6)",
expectedArgs: []interface{}{
anyArg{},
uint64(15),
true,
true,
true,
"agg-id",
},
},
@@ -131,7 +135,8 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
instance.AggregateType,
[]byte(`{
"userLoginMustBeDomain": true,
"validateOrgDomains": true
"validateOrgDomains": true,
"smtpSenderAddressMatchesInstanceDomain": true
}`),
), instance.DomainPolicyAddedEventMapper),
},
@@ -143,7 +148,7 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
executer: &testExecuter{
executions: []execution{
{
expectedStmt: "INSERT INTO projections.domain_policies (creation_date, change_date, sequence, id, state, user_login_must_be_domain, validate_org_domains, is_default, resource_owner, instance_id) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)",
expectedStmt: "INSERT INTO projections.domain_policies (creation_date, change_date, sequence, id, state, user_login_must_be_domain, validate_org_domains, smtp_sender_address_matches_instance_domain, is_default, resource_owner, instance_id) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11)",
expectedArgs: []interface{}{
anyArg{},
anyArg{},
@@ -153,6 +158,7 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
true,
true,
true,
true,
"ro-id",
"instance-id",
},
@@ -170,7 +176,8 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
instance.AggregateType,
[]byte(`{
"userLoginMustBeDomain": true,
"validateOrgDomains": true
"validateOrgDomains": true,
"smtpSenderAddressMatchesInstanceDomain": true
}`),
), instance.DomainPolicyChangedEventMapper),
},
@@ -182,12 +189,13 @@ func TestDomainPolicyProjection_reduces(t *testing.T) {
executer: &testExecuter{
executions: []execution{
{
expectedStmt: "UPDATE projections.domain_policies SET (change_date, sequence, user_login_must_be_domain, validate_org_domains) = ($1, $2, $3, $4) WHERE (id = $5)",
expectedStmt: "UPDATE projections.domain_policies SET (change_date, sequence, user_login_must_be_domain, validate_org_domains, smtp_sender_address_matches_instance_domain) = ($1, $2, $3, $4, $5) WHERE (id = $6)",
expectedArgs: []interface{}{
anyArg{},
uint64(15),
true,
true,
true,
"agg-id",
},
},