mirror of
https://github.com/zitadel/zitadel.git
synced 2024-12-14 03:54:21 +00:00
f37113194d
Add a check for circular includes in action v2 executions, so that no self-includes or infinite loops can happen. Closes #7445 ### Definition of Ready - [x] I am happy with the code - [x] Short description of the feature/issue is added in the pr description - [x] PR is linked to the corresponding user story - [x] Acceptance criteria are met - [x] All open todos and follow ups are defined in a new ticket and justified - [x] Deviations from the acceptance criteria and design are agreed with the PO and documented. - [x] No debug or dead code - [x] My code has no repetitions - [x] Critical parts are tested automatically - [x] Where possible E2E tests are implemented - [x] Documentation/examples are up-to-date - [x] All non-functional requirements are met - [x] Functionality of the acceptance criteria is checked manually on the dev system. --------- Co-authored-by: Livio Spring <livio.a@gmail.com>
2873 lines
61 KiB
Go
2873 lines
61 KiB
Go
package command
|
|
|
|
import (
|
|
"context"
|
|
"testing"
|
|
"time"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
|
|
"github.com/zitadel/zitadel/internal/domain"
|
|
"github.com/zitadel/zitadel/internal/eventstore"
|
|
"github.com/zitadel/zitadel/internal/repository/execution"
|
|
"github.com/zitadel/zitadel/internal/repository/target"
|
|
"github.com/zitadel/zitadel/internal/zerrors"
|
|
)
|
|
|
|
func existsMock(exists bool) func(method string) bool {
|
|
return func(method string) bool {
|
|
return exists
|
|
}
|
|
}
|
|
func TestCommands_SetExecutionRequest(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
grpcMethodExists func(method string) bool
|
|
grpcServiceExists func(method string) bool
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionAPICondition
|
|
set *SetExecution
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no valid cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"notvalid",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty executionType, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty target, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"method not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"service not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcServiceExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, method target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
target.NewAddedEvent(context.Background(),
|
|
target.NewAggregate("target", "instance"),
|
|
"name",
|
|
domain.TargetTypeWebhook,
|
|
"https://example.com",
|
|
time.Second,
|
|
true,
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/method", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, service target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
target.NewAddedEvent(context.Background(),
|
|
target.NewAggregate("target", "instance"),
|
|
"name",
|
|
domain.TargetTypeWebhook,
|
|
"https://example.com",
|
|
time.Second,
|
|
true,
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/service", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcServiceExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, all target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
target.NewAddedEvent(context.Background(),
|
|
target.NewAggregate("target", "instance"),
|
|
"name",
|
|
domain.TargetTypeWebhook,
|
|
"https://example.com",
|
|
time.Second,
|
|
true,
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push not found, method include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, method include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/method", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push not found, service include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
grpcServiceExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, service include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/service", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcServiceExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push not found, all include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, all include",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "request/include"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
GrpcMethodExisting: tt.fields.grpcMethodExists,
|
|
GrpcServiceExisting: tt.fields.grpcServiceExists,
|
|
}
|
|
details, err := c.SetExecutionRequest(tt.args.ctx, tt.args.cond, tt.args.set, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_SetExecutionResponse(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
grpcMethodExists func(method string) bool
|
|
grpcServiceExists func(method string) bool
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionAPICondition
|
|
set *SetExecution
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no valid cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"notvalid",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty executionType, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty target, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
target.NewAddedEvent(context.Background(),
|
|
target.NewAggregate("target", "instance"),
|
|
"name",
|
|
domain.TargetTypeWebhook,
|
|
"https://example.com",
|
|
time.Second,
|
|
true,
|
|
),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"method not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcMethodExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"service not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
grpcServiceExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, method target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
target.NewAddedEvent(context.Background(),
|
|
target.NewAggregate("target", "instance"),
|
|
"name",
|
|
domain.TargetTypeWebhook,
|
|
"https://example.com",
|
|
time.Second,
|
|
true,
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/method", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcMethodExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, service target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/service", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
grpcServiceExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, all target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
GrpcMethodExisting: tt.fields.grpcMethodExists,
|
|
GrpcServiceExisting: tt.fields.grpcServiceExists,
|
|
}
|
|
details, err := c.SetExecutionResponse(tt.args.ctx, tt.args.cond, tt.args.set, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_SetExecutionEvent(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
eventExists func(string) bool
|
|
eventGroupExists func(string) bool
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionEventCondition
|
|
set *SetExecution
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no valid cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"notvalid",
|
|
"notvalid",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty executionType, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
eventExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty target, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
eventExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"notvalid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
eventExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"event not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
eventExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"event",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"group not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
eventGroupExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"group",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, event target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/event", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
eventExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"event",
|
|
"",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, group target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/group.*", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
eventGroupExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"group",
|
|
false,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, all target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
EventExisting: tt.fields.eventExists,
|
|
EventGroupExisting: tt.fields.eventGroupExists,
|
|
}
|
|
details, err := c.SetExecutionEvent(tt.args.ctx, tt.args.cond, tt.args.set, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_SetExecutionFunction(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
actionFunctionExists func(string) bool
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond ExecutionFunctionCondition
|
|
set *SetExecution
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "",
|
|
set: &SetExecution{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "",
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty executionType, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"empty target, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
}, {
|
|
"push error, function target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push error, function not existing",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
actionFunctionExists: existsMock(false),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, function target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
targetAddEvent("target", "instance"),
|
|
),
|
|
expectPush(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
actionFunctionExists: existsMock(true),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
set: &SetExecution{
|
|
Targets: []*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
ActionFunctionExisting: tt.fields.actionFunctionExists,
|
|
}
|
|
details, err := c.SetExecutionFunction(tt.args.ctx, tt.args.cond, tt.args.set, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_DeleteExecutionRequest(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionAPICondition
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no valid cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"notvalid",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("request/valid", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, method target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/method", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("request/method", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, service target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/service", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("request/service", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, all target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("request", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
}
|
|
details, err := c.DeleteExecutionRequest(tt.args.ctx, tt.args.cond, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_DeleteExecutionResponse(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionAPICondition
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no valid cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"notvalid",
|
|
"notvalid",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("response/valid", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"not found, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, method target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/method", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("response/method", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"method",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, service target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response/service", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("response/service", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"service",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push ok, all target",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("response", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("response", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionAPICondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
}
|
|
details, err := c.DeleteExecutionResponse(tt.args.ctx, tt.args.cond, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_DeleteExecutionEvent(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond *ExecutionEventCondition
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{},
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("event/valid", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"push error, not existing",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push error, event",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, event",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/valid", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("event/valid", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"valid",
|
|
"",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push error, group",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"valid",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, group",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event/group", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("event/group.*", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"group",
|
|
false,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"push error, all",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, all",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("event", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("event", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: &ExecutionEventCondition{
|
|
"",
|
|
"",
|
|
true,
|
|
},
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
}
|
|
details, err := c.DeleteExecutionEvent(tt.args.ctx, tt.args.cond, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestCommands_DeleteExecutionFunction(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cond ExecutionFunctionCondition
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
details *domain.ObjectDetails
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"no resourceowner, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "",
|
|
resourceOwner: "",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"no cond, error",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsErrorInvalidArgument,
|
|
},
|
|
},
|
|
{
|
|
"push failed, error",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPushFailed(
|
|
zerrors.ThrowPreconditionFailed(nil, "id", "name already exists"),
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"push error, not existing",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
err: zerrors.IsNotFound,
|
|
},
|
|
},
|
|
{
|
|
"push ok, function",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
expectPush(
|
|
execution.NewRemovedEvent(context.Background(),
|
|
execution.NewAggregate("function/function", "instance"),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cond: "function",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
details: &domain.ObjectDetails{
|
|
ResourceOwner: "instance",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
}
|
|
details, err := c.DeleteExecutionFunction(tt.args.ctx, tt.args.cond, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.details, details)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func mockExecutionIncludesCache(cache map[string][]string) includeCacheFunc {
|
|
return func(ctx context.Context, id string, resourceOwner string) ([]string, error) {
|
|
included, ok := cache[id]
|
|
if !ok {
|
|
return nil, zerrors.ThrowPreconditionFailed(nil, "", "cache failed")
|
|
}
|
|
return included, nil
|
|
}
|
|
}
|
|
|
|
func TestCommands_checkForIncludeCircular(t *testing.T) {
|
|
type args struct {
|
|
ctx context.Context
|
|
id string
|
|
resourceOwner string
|
|
includes []string
|
|
cache map[string][]string
|
|
}
|
|
type res struct {
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"not found, error",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id",
|
|
resourceOwner: "",
|
|
includes: []string{"notexistent"},
|
|
cache: map[string][]string{},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"single, ok",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id2"},
|
|
cache: map[string][]string{
|
|
"id2": {},
|
|
},
|
|
},
|
|
res{},
|
|
},
|
|
{
|
|
"single, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id1"},
|
|
cache: map[string][]string{},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 3, ok",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id2"},
|
|
cache: map[string][]string{
|
|
"id2": {"id3"},
|
|
"id3": {},
|
|
},
|
|
},
|
|
res{},
|
|
},
|
|
{
|
|
"multi 3, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id2"},
|
|
cache: map[string][]string{
|
|
"id2": {"id3"},
|
|
"id3": {"id1"},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 5, ok",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id11", "id12"},
|
|
cache: map[string][]string{
|
|
"id11": {"id21", "id23"},
|
|
"id12": {"id22"},
|
|
"id21": {},
|
|
"id22": {},
|
|
"id23": {},
|
|
},
|
|
},
|
|
res{},
|
|
},
|
|
{
|
|
"multi 5, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id11", "id12"},
|
|
cache: map[string][]string{
|
|
"id11": {"id21", "id23"},
|
|
"id12": {"id22"},
|
|
"id21": {},
|
|
"id22": {},
|
|
"id23": {"id1"},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 5, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id11", "id12"},
|
|
cache: map[string][]string{
|
|
"id11": {"id21", "id23"},
|
|
"id12": {"id22"},
|
|
"id21": {},
|
|
"id22": {},
|
|
"id23": {"id11"},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 5, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id11", "id12"},
|
|
cache: map[string][]string{
|
|
"id11": {"id21", "id23"},
|
|
"id12": {"id22"},
|
|
"id21": {"id11"},
|
|
"id22": {},
|
|
"id23": {},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 5, circular",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id11", "id12"},
|
|
cache: map[string][]string{
|
|
"id11": {"id21", "id23"},
|
|
"id12": {"id22"},
|
|
"id21": {},
|
|
"id22": {"id12"},
|
|
"id23": {},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
{
|
|
"multi 3, maxlevel",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id2"},
|
|
cache: map[string][]string{
|
|
"id2": {"id3"},
|
|
"id3": {},
|
|
},
|
|
},
|
|
res{},
|
|
},
|
|
{
|
|
"multi 4, over maxlevel",
|
|
args{
|
|
ctx: context.Background(),
|
|
id: "id1",
|
|
resourceOwner: "",
|
|
includes: []string{"id2"},
|
|
cache: map[string][]string{
|
|
"id2": {"id3"},
|
|
"id3": {"id4"},
|
|
"id4": {},
|
|
},
|
|
},
|
|
res{
|
|
err: zerrors.IsPreconditionFailed,
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
f := mockExecutionIncludesCache(tt.args.cache)
|
|
err := checkForIncludeCircular(tt.args.ctx, tt.args.id, tt.args.resourceOwner, tt.args.includes, f, 3)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func mockExecutionIncludesCacheFuncs(cache map[string][]string) (func(string) ([]string, bool), func(string, []string)) {
|
|
return func(s string) ([]string, bool) {
|
|
includes, ok := cache[s]
|
|
return includes, ok
|
|
}, func(s string, strings []string) {
|
|
cache[s] = strings
|
|
}
|
|
}
|
|
|
|
func TestCommands_getExecutionIncludes(t *testing.T) {
|
|
type fields struct {
|
|
eventstore func(t *testing.T) *eventstore.Eventstore
|
|
}
|
|
type args struct {
|
|
ctx context.Context
|
|
cache map[string][]string
|
|
id string
|
|
resourceOwner string
|
|
}
|
|
type res struct {
|
|
includes []string
|
|
cache map[string][]string
|
|
err func(error) bool
|
|
}
|
|
tests := []struct {
|
|
name string
|
|
fields fields
|
|
args args
|
|
res res
|
|
}{
|
|
{
|
|
"new empty, ok",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{},
|
|
cache: map[string][]string{"id": {}},
|
|
},
|
|
},
|
|
{
|
|
"new includes, ok",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "include"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{"include"},
|
|
cache: map[string][]string{"id": {"include"}},
|
|
},
|
|
},
|
|
{
|
|
"found, ok",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{"id": nil},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: nil,
|
|
cache: map[string][]string{"id": nil},
|
|
},
|
|
},
|
|
{
|
|
"found includes, ok",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{"id": {"include1", "include2", "include3"}},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{"include1", "include2", "include3"},
|
|
cache: map[string][]string{"id": {"include1", "include2", "include3"}},
|
|
},
|
|
},
|
|
{
|
|
"found multiple, ok",
|
|
fields{
|
|
eventstore: expectEventstore(),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
},
|
|
id: "id2",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{"include1", "include2", "include3"},
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"new multiple, ok",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeTarget, Target: "target"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{},
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
"id": {},
|
|
},
|
|
},
|
|
},
|
|
{
|
|
"new multiple includes, ok",
|
|
fields{
|
|
eventstore: expectEventstore(
|
|
expectFilter(
|
|
eventFromEventPusher(
|
|
execution.NewSetEventV2(context.Background(),
|
|
execution.NewAggregate("request/include", "instance"),
|
|
[]*execution.Target{
|
|
{Type: domain.ExecutionTargetTypeInclude, Target: "include"},
|
|
},
|
|
),
|
|
),
|
|
),
|
|
),
|
|
},
|
|
args{
|
|
ctx: context.Background(),
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
},
|
|
id: "id",
|
|
resourceOwner: "instance",
|
|
},
|
|
res{
|
|
includes: []string{"include"},
|
|
cache: map[string][]string{
|
|
"id1": {"include1", "include2", "include3"},
|
|
"id2": {"include1", "include2", "include3"},
|
|
"id3": {"include1", "include2", "include3"},
|
|
"id": {"include"},
|
|
},
|
|
},
|
|
},
|
|
}
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
c := &Commands{
|
|
eventstore: tt.fields.eventstore(t),
|
|
}
|
|
includes, err := c.getExecutionIncludes(mockExecutionIncludesCacheFuncs(tt.args.cache))(tt.args.ctx, tt.args.id, tt.args.resourceOwner)
|
|
if tt.res.err == nil {
|
|
assert.NoError(t, err)
|
|
}
|
|
if tt.res.err != nil && !tt.res.err(err) {
|
|
t.Errorf("got wrong err: %v ", err)
|
|
}
|
|
if tt.res.err == nil {
|
|
assert.Equal(t, tt.res.cache, tt.args.cache)
|
|
assert.Equal(t, tt.res.includes, includes)
|
|
}
|
|
})
|
|
}
|
|
}
|