mirror of
https://github.com/zitadel/zitadel.git
synced 2025-08-12 07:57:32 +00:00
feat: delete (#243)
* feat: project role remove * feat: search queries * feat: search queries * feat: cascade remove/change project role * fix: comment in project grant * fix: remove projecr grant * fix: only search usergrants of my org * fix: delete usergrants * fix: delete usergrants * fix: check if role exists on project grant * feat: bulk add project role * fix: tests * fix: update user grants on project update * fix: return roles * feat: add resourceowner name on project grants * fix: migration number * fix: tests * fix: generate protos * fix: some unnecessary code
This commit is contained in:
@@ -248,28 +248,37 @@ func (es *ProjectEventstore) RemoveProjectMember(ctx context.Context, member *pr
|
||||
return err
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) AddProjectRole(ctx context.Context, role *proj_model.ProjectRole) (*proj_model.ProjectRole, error) {
|
||||
if !role.IsValid() {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-idue3", "Key is required")
|
||||
func (es *ProjectEventstore) AddProjectRoles(ctx context.Context, roles ...*proj_model.ProjectRole) (*proj_model.ProjectRole, error) {
|
||||
if roles == nil || len(roles) == 0 {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-idue3", "must be at least one role")
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, role.AggregateID)
|
||||
for _, role := range roles {
|
||||
if !role.IsValid() {
|
||||
return nil, caos_errs.ThrowPreconditionFailedf(nil, "EVENT-idue3", "role is invalid %v", role)
|
||||
}
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, roles[0].AggregateID)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if existing.ContainsRole(role) {
|
||||
return nil, caos_errs.ThrowAlreadyExists(nil, "EVENT-sk35t", "Project contains role with same key")
|
||||
for _, role := range roles {
|
||||
if existing.ContainsRole(role) {
|
||||
return nil, caos_errs.ThrowAlreadyExists(nil, "EVENT-sk35t", "Project contains role with same key")
|
||||
}
|
||||
}
|
||||
|
||||
repoProject := model.ProjectFromModel(existing)
|
||||
repoRole := model.ProjectRoleFromModel(role)
|
||||
projectAggregate := ProjectRoleAddedAggregate(es.Eventstore.AggregateCreator(), repoProject, repoRole)
|
||||
repoRoles := model.ProjectRolesFromModel(roles)
|
||||
projectAggregate := ProjectRoleAddedAggregate(es.Eventstore.AggregateCreator(), repoProject, repoRoles...)
|
||||
err = es_sdk.Push(ctx, es.PushAggregates, repoProject.AppendEvents, projectAggregate)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if len(repoRoles) > 1 {
|
||||
return nil, nil
|
||||
}
|
||||
es.projectCache.cacheProject(repoProject)
|
||||
|
||||
if _, r := model.GetProjectRole(repoProject.Roles, role.Key); r != nil {
|
||||
if _, r := model.GetProjectRole(repoProject.Roles, repoRoles[0].Key); r != nil {
|
||||
return model.ProjectRoleToModel(r), nil
|
||||
}
|
||||
return nil, caos_errs.ThrowInternal(nil, "EVENT-sie83", "Could not find role in list")
|
||||
@@ -302,25 +311,52 @@ func (es *ProjectEventstore) ChangeProjectRole(ctx context.Context, role *proj_m
|
||||
return nil, caos_errs.ThrowInternal(nil, "EVENT-sl1or", "Could not find role in list")
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) RemoveProjectRole(ctx context.Context, role *proj_model.ProjectRole) error {
|
||||
func (es *ProjectEventstore) PrepareRemoveProjectRole(ctx context.Context, role *proj_model.ProjectRole) (*model.Project, *es_models.Aggregate, error) {
|
||||
if role.Key == "" {
|
||||
return caos_errs.ThrowPreconditionFailed(nil, "EVENT-id823", "Key is required")
|
||||
return nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-id823", "Key is required")
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, role.AggregateID)
|
||||
if err != nil {
|
||||
return err
|
||||
return nil, nil, err
|
||||
}
|
||||
if !existing.ContainsRole(role) {
|
||||
return caos_errs.ThrowPreconditionFailed(nil, "EVENT-oe823", "Role doesn't exist on project")
|
||||
return nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-oe823", "Role doesn't exist on project")
|
||||
}
|
||||
repoProject := model.ProjectFromModel(existing)
|
||||
repoRole := model.ProjectRoleFromModel(role)
|
||||
projectAggregate := ProjectRoleRemovedAggregate(es.Eventstore.AggregateCreator(), repoProject, repoRole)
|
||||
err = es_sdk.Push(ctx, es.PushAggregates, repoProject.AppendEvents, projectAggregate)
|
||||
grants := es.RemoveRoleFromGrants(repoProject, role.Key)
|
||||
projectAggregate, err := ProjectRoleRemovedAggregate(ctx, es.Eventstore.AggregateCreator(), repoProject, repoRole, grants)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
return repoProject, projectAggregate, nil
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) RemoveRoleFromGrants(existing *model.Project, roleKey string) []*model.ProjectGrant {
|
||||
grants := make([]*model.ProjectGrant, 0)
|
||||
for _, grant := range existing.Grants {
|
||||
for i, role := range grant.RoleKeys {
|
||||
if role == roleKey {
|
||||
grant.RoleKeys[i] = grant.RoleKeys[len(grant.RoleKeys)-1]
|
||||
grant.RoleKeys[len(grant.RoleKeys)-1] = ""
|
||||
grant.RoleKeys = grant.RoleKeys[:len(grant.RoleKeys)-1]
|
||||
grants = append(grants, grant)
|
||||
}
|
||||
}
|
||||
}
|
||||
return grants
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) RemoveProjectRole(ctx context.Context, role *proj_model.ProjectRole) error {
|
||||
project, aggregate, err := es.PrepareRemoveProjectRole(ctx, role)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
es.projectCache.cacheProject(repoProject)
|
||||
err = es_sdk.PushAggregates(ctx, es.PushAggregates, project.AppendEvents, aggregate)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
es.projectCache.cacheProject(project)
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -766,50 +802,34 @@ func (es *ProjectEventstore) AddProjectGrant(ctx context.Context, grant *proj_mo
|
||||
return nil, caos_errs.ThrowInternal(nil, "EVENT-sk3t5", "Could not find grant in list")
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) ChangeProjectGrant(ctx context.Context, grant *proj_model.ProjectGrant) (*proj_model.ProjectGrant, error) {
|
||||
func (es *ProjectEventstore) PrepareChangeProjectGrant(ctx context.Context, grant *proj_model.ProjectGrant) (*model.Project, func(ctx context.Context) (*es_models.Aggregate, error), []string, error) {
|
||||
if grant == nil && grant.GrantID == "" {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-8sie3", "invalid grant")
|
||||
return nil, nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-8sie3", "invalid grant")
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, grant.AggregateID)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, nil, nil, err
|
||||
}
|
||||
if _, g := existing.GetGrant(grant.GrantID); g == nil {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-die83", "Grant not existing on project")
|
||||
_, existingGrant := existing.GetGrant(grant.GrantID)
|
||||
if existingGrant == nil {
|
||||
return nil, nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-die83", "Grant not existing on project")
|
||||
}
|
||||
if !existing.ContainsRoles(grant.RoleKeys) {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-di83d", "One role doesnt exist in Project")
|
||||
return nil, nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-di83d", "One role doesnt exist in Project")
|
||||
}
|
||||
removedRoles := existingGrant.GetRemovedRoles(grant.RoleKeys)
|
||||
repoProject := model.ProjectFromModel(existing)
|
||||
repoGrant := model.GrantFromModel(grant)
|
||||
|
||||
projectAggregate := ProjectGrantChangedAggregate(es.Eventstore.AggregateCreator(), repoProject, repoGrant)
|
||||
err = es_sdk.Push(ctx, es.PushAggregates, repoProject.AppendEvents, projectAggregate)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
es.projectCache.cacheProject(repoProject)
|
||||
|
||||
if _, g := model.GetProjectGrant(repoProject.Grants, grant.GrantID); g != nil {
|
||||
return model.GrantToModel(g), nil
|
||||
}
|
||||
return nil, caos_errs.ThrowInternal(nil, "EVENT-dksi8", "Could not find app in list")
|
||||
return repoProject, projectAggregate, removedRoles, nil
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) RemoveProjectGrant(ctx context.Context, grant *proj_model.ProjectGrant) error {
|
||||
if grant.GrantID == "" {
|
||||
return caos_errs.ThrowPreconditionFailed(nil, "EVENT-8eud6", "GrantId is required")
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, grant.AggregateID)
|
||||
repoProject, projectAggregate, err := es.PrepareRemoveProjectGrant(ctx, grant)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if _, g := existing.GetGrant(grant.GrantID); g == nil {
|
||||
return caos_errs.ThrowPreconditionFailed(nil, "EVENT-9ie3s", "Grant doesn't exist on project")
|
||||
}
|
||||
repoProject := model.ProjectFromModel(existing)
|
||||
grantRepo := model.GrantFromModel(grant)
|
||||
projectAggregate := ProjectGrantRemovedAggregate(es.Eventstore.AggregateCreator(), repoProject, grantRepo)
|
||||
err = es_sdk.Push(ctx, es.PushAggregates, repoProject.AppendEvents, projectAggregate)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -818,6 +838,39 @@ func (es *ProjectEventstore) RemoveProjectGrant(ctx context.Context, grant *proj
|
||||
return nil
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) RemoveProjectGrants(ctx context.Context, grants ...*proj_model.ProjectGrant) error {
|
||||
aggregates := make([]*es_models.Aggregate, len(grants))
|
||||
for i, grant := range grants {
|
||||
_, projectAggregate, err := es.PrepareRemoveProjectGrant(ctx, grant)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
agg, err := projectAggregate(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
aggregates[i] = agg
|
||||
}
|
||||
return es_sdk.PushAggregates(ctx, es.PushAggregates, nil, aggregates...)
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) PrepareRemoveProjectGrant(ctx context.Context, grant *proj_model.ProjectGrant) (*model.Project, func(ctx context.Context) (*es_models.Aggregate, error), error) {
|
||||
if grant.GrantID == "" {
|
||||
return nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-8eud6", "GrantId is required")
|
||||
}
|
||||
existing, err := es.ProjectByID(ctx, grant.AggregateID)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
if _, g := existing.GetGrant(grant.GrantID); g == nil {
|
||||
return nil, nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-9ie3s", "Grant doesn't exist on project")
|
||||
}
|
||||
repoProject := model.ProjectFromModel(existing)
|
||||
grantRepo := model.GrantFromModel(grant)
|
||||
projectAggregate := ProjectGrantRemovedAggregate(es.Eventstore.AggregateCreator(), repoProject, grantRepo)
|
||||
return repoProject, projectAggregate, nil
|
||||
}
|
||||
|
||||
func (es *ProjectEventstore) DeactivateProjectGrant(ctx context.Context, projectID, grantID string) (*proj_model.ProjectGrant, error) {
|
||||
if grantID == "" {
|
||||
return nil, caos_errs.ThrowPreconditionFailed(nil, "EVENT-7due2", "grantID missing")
|
||||
|
@@ -3,7 +3,6 @@ package eventsourcing
|
||||
import (
|
||||
"context"
|
||||
"encoding/json"
|
||||
"reflect"
|
||||
"testing"
|
||||
|
||||
"github.com/caos/zitadel/internal/api/auth"
|
||||
@@ -707,9 +706,9 @@ func TestRemoveProjectMember(t *testing.T) {
|
||||
func TestAddProjectRole(t *testing.T) {
|
||||
ctrl := gomock.NewController(t)
|
||||
type args struct {
|
||||
es *ProjectEventstore
|
||||
ctx context.Context
|
||||
role *model.ProjectRole
|
||||
es *ProjectEventstore
|
||||
ctx context.Context
|
||||
roles []*model.ProjectRole
|
||||
}
|
||||
type res struct {
|
||||
result *model.ProjectRole
|
||||
@@ -724,9 +723,9 @@ func TestAddProjectRole(t *testing.T) {
|
||||
{
|
||||
name: "add project role, ok",
|
||||
args: args{
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
role: &model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"},
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
roles: []*model.ProjectRole{&model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"}},
|
||||
},
|
||||
res: res{
|
||||
result: &model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"},
|
||||
@@ -735,9 +734,9 @@ func TestAddProjectRole(t *testing.T) {
|
||||
{
|
||||
name: "no key",
|
||||
args: args{
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
role: &model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, DisplayName: "DisplayName", Group: "Group"},
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
roles: []*model.ProjectRole{&model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, DisplayName: "DisplayName", Group: "Group"}},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
@@ -747,9 +746,9 @@ func TestAddProjectRole(t *testing.T) {
|
||||
{
|
||||
name: "role already existing",
|
||||
args: args{
|
||||
es: GetMockManipulateProjectWithRole(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
role: &model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"},
|
||||
es: GetMockManipulateProjectWithRole(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
roles: []*model.ProjectRole{&model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"}},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
@@ -759,9 +758,9 @@ func TestAddProjectRole(t *testing.T) {
|
||||
{
|
||||
name: "existing project not found",
|
||||
args: args{
|
||||
es: GetMockManipulateProjectNoEvents(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
role: &model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"},
|
||||
es: GetMockManipulateProjectNoEvents(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
roles: []*model.ProjectRole{&model.ProjectRole{ObjectRoot: es_models.ObjectRoot{AggregateID: "AggregateID", Sequence: 1}, Key: "Key", DisplayName: "DisplayName", Group: "Group"}},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
@@ -771,7 +770,7 @@ func TestAddProjectRole(t *testing.T) {
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
result, err := tt.args.es.AddProjectRole(tt.args.ctx, tt.args.role)
|
||||
result, err := tt.args.es.AddProjectRoles(tt.args.ctx, tt.args.roles...)
|
||||
|
||||
if !tt.res.wantErr && result.AggregateID == "" {
|
||||
t.Errorf("result has no id")
|
||||
@@ -1950,126 +1949,6 @@ func TestAddProjectGrant(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestChangeProjectGrant(t *testing.T) {
|
||||
ctrl := gomock.NewController(t)
|
||||
type args struct {
|
||||
es *ProjectEventstore
|
||||
ctx context.Context
|
||||
grant *model.ProjectGrant
|
||||
}
|
||||
type res struct {
|
||||
result *model.ProjectGrant
|
||||
wantErr bool
|
||||
errFunc func(err error) bool
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
args args
|
||||
res res
|
||||
}{
|
||||
{
|
||||
name: "change grant, ok",
|
||||
args: args{
|
||||
es: GetMockManipulateProjectWithGrantExistingRole(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
grant: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
GrantedOrgID: "GrantedOrgID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
res: res{
|
||||
result: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
GrantedOrgID: "GrantedOrgID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "invalid grant",
|
||||
args: args{
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
grant: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "grant not existing",
|
||||
args: args{
|
||||
es: GetMockManipulateProject(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
grant: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
GrantedOrgID: "GrantedOrgID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "role not existing",
|
||||
args: args{
|
||||
es: GetMockManipulateProjectWithGrant(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
grant: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
GrantedOrgID: "GrantedOrgID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "existing project not found",
|
||||
args: args{
|
||||
es: GetMockManipulateProjectNoEvents(ctrl),
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
grant: &model.ProjectGrant{ObjectRoot: es_models.ObjectRoot{AggregateID: "ID", Sequence: 1},
|
||||
GrantID: "GrantID",
|
||||
GrantedOrgID: "GrantedOrgID",
|
||||
RoleKeys: []string{"KeyChanged"},
|
||||
},
|
||||
},
|
||||
res: res{
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsNotFound,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
result, err := tt.args.es.ChangeProjectGrant(tt.args.ctx, tt.args.grant)
|
||||
|
||||
if !tt.res.wantErr && result.AggregateID == "" {
|
||||
t.Errorf("result has no id")
|
||||
}
|
||||
if !tt.res.wantErr && result.GrantID != tt.res.result.GrantID {
|
||||
t.Errorf("got wrong result GrantID: expected: %v, actual: %v ", tt.res.result.GrantID, result.GrantID)
|
||||
}
|
||||
if !tt.res.wantErr && !reflect.DeepEqual(result.RoleKeys, tt.res.result.RoleKeys) {
|
||||
t.Errorf("got wrong result name: expected: %v, actual: %v ", tt.res.result.RoleKeys, result.GrantID)
|
||||
}
|
||||
if tt.res.wantErr && !tt.res.errFunc(err) {
|
||||
t.Errorf("got wrong err: %v ", err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestRemoveProjectGrant(t *testing.T) {
|
||||
ctrl := gomock.NewController(t)
|
||||
type args struct {
|
||||
|
@@ -127,7 +127,7 @@ func (p *Project) AppendEvent(event *es_models.Event) error {
|
||||
return p.appendChangeOIDCConfigEvent(event)
|
||||
case ProjectGrantAdded:
|
||||
return p.appendAddGrantEvent(event)
|
||||
case ProjectGrantChanged:
|
||||
case ProjectGrantChanged, ProjectGrantCascadeChanged:
|
||||
return p.appendChangeGrantEvent(event)
|
||||
case ProjectGrantDeactivated:
|
||||
return p.appendGrantStateEvent(event, model.PROJECTGRANTSTATE_INACTIVE)
|
||||
|
@@ -31,9 +31,9 @@ func GetProjectGrant(grants []*ProjectGrant, id string) (int, *ProjectGrant) {
|
||||
return -1, nil
|
||||
}
|
||||
|
||||
func GetProjectGrantByResourceOwner(grants []*ProjectGrant, resourceOwner string) (int, *ProjectGrant) {
|
||||
func GetProjectGrantByOrgID(grants []*ProjectGrant, resourceOwner string) (int, *ProjectGrant) {
|
||||
for i, g := range grants {
|
||||
if g.ResourceOwner == resourceOwner {
|
||||
if g.GrantedOrgID == resourceOwner {
|
||||
return i, g
|
||||
}
|
||||
}
|
||||
|
@@ -19,11 +19,12 @@ const (
|
||||
ProjectRoleChanged models.EventType = "project.role.changed"
|
||||
ProjectRoleRemoved models.EventType = "project.role.removed"
|
||||
|
||||
ProjectGrantAdded models.EventType = "project.grant.added"
|
||||
ProjectGrantChanged models.EventType = "project.grant.changed"
|
||||
ProjectGrantRemoved models.EventType = "project.grant.removed"
|
||||
ProjectGrantDeactivated models.EventType = "project.grant.deactivated"
|
||||
ProjectGrantReactivated models.EventType = "project.grant.reactivated"
|
||||
ProjectGrantAdded models.EventType = "project.grant.added"
|
||||
ProjectGrantChanged models.EventType = "project.grant.changed"
|
||||
ProjectGrantRemoved models.EventType = "project.grant.removed"
|
||||
ProjectGrantDeactivated models.EventType = "project.grant.deactivated"
|
||||
ProjectGrantReactivated models.EventType = "project.grant.reactivated"
|
||||
ProjectGrantCascadeChanged models.EventType = "project.grant.cascade.changed"
|
||||
|
||||
ProjectGrantMemberAdded models.EventType = "project.grant.member.added"
|
||||
ProjectGrantMemberChanged models.EventType = "project.grant.member.changed"
|
||||
|
@@ -144,16 +144,22 @@ func ProjectMemberRemovedAggregate(aggCreator *es_models.AggregateCreator, exist
|
||||
}
|
||||
}
|
||||
|
||||
func ProjectRoleAddedAggregate(aggCreator *es_models.AggregateCreator, existing *model.Project, role *model.ProjectRole) func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
func ProjectRoleAddedAggregate(aggCreator *es_models.AggregateCreator, existing *model.Project, roles ...*model.ProjectRole) func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
return func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
if role == nil {
|
||||
return nil, errors.ThrowPreconditionFailed(nil, "EVENT-sleo9", "role should not be nil")
|
||||
if roles == nil {
|
||||
return nil, errors.ThrowPreconditionFailed(nil, "EVENT-sleo9", "roles should not be nil")
|
||||
}
|
||||
agg, err := ProjectAggregate(ctx, aggCreator, existing)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return agg.AppendEvent(model.ProjectRoleAdded, role)
|
||||
for _, role := range roles {
|
||||
agg, err = agg.AppendEvent(model.ProjectRoleAdded, role)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
return agg, nil
|
||||
}
|
||||
}
|
||||
|
||||
@@ -170,17 +176,29 @@ func ProjectRoleChangedAggregate(aggCreator *es_models.AggregateCreator, existin
|
||||
}
|
||||
}
|
||||
|
||||
func ProjectRoleRemovedAggregate(aggCreator *es_models.AggregateCreator, existing *model.Project, role *model.ProjectRole) func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
return func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
if role == nil {
|
||||
return nil, errors.ThrowPreconditionFailed(nil, "EVENT-d8eis", "member should not be nil")
|
||||
}
|
||||
agg, err := ProjectAggregate(ctx, aggCreator, existing)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return agg.AppendEvent(model.ProjectRoleRemoved, role)
|
||||
func ProjectRoleRemovedAggregate(ctx context.Context, aggCreator *es_models.AggregateCreator, existing *model.Project, role *model.ProjectRole, grants []*model.ProjectGrant) (*es_models.Aggregate, error) {
|
||||
if role == nil {
|
||||
return nil, errors.ThrowPreconditionFailed(nil, "EVENT-d8eis", "member should not be nil")
|
||||
}
|
||||
agg, err := ProjectAggregate(ctx, aggCreator, existing)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
agg, err = agg.AppendEvent(model.ProjectRoleRemoved, role)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
for _, grant := range grants {
|
||||
var changes map[string]interface{}
|
||||
if _, g := model.GetProjectGrant(existing.Grants, grant.GrantID); grant != nil {
|
||||
changes = g.Changes(grant)
|
||||
agg, err = agg.AppendEvent(model.ProjectGrantCascadeChanged, changes)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
}
|
||||
return agg, nil
|
||||
}
|
||||
|
||||
func ApplicationAddedAggregate(aggCreator *es_models.AggregateCreator, existing *model.Project, app *model.Application) func(ctx context.Context) (*es_models.Aggregate, error) {
|
||||
|
@@ -694,7 +694,7 @@ func TestProjectRoleAddedAggregate(t *testing.T) {
|
||||
type args struct {
|
||||
ctx context.Context
|
||||
existing *model.Project
|
||||
new *model.ProjectRole
|
||||
new []*model.ProjectRole
|
||||
aggCreator *models.AggregateCreator
|
||||
}
|
||||
type res struct {
|
||||
@@ -713,7 +713,7 @@ func TestProjectRoleAddedAggregate(t *testing.T) {
|
||||
args: args{
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
existing: &model.Project{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Name: "ProjectName", State: int32(proj_model.PROJECTSTATE_ACTIVE)},
|
||||
new: &model.ProjectRole{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Key: "Key"},
|
||||
new: []*model.ProjectRole{&model.ProjectRole{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Key: "Key"}},
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
@@ -721,6 +721,22 @@ func TestProjectRoleAddedAggregate(t *testing.T) {
|
||||
eventType: model.ProjectRoleAdded,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "projectrole multiple added ok",
|
||||
args: args{
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
existing: &model.Project{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Name: "ProjectName", State: int32(proj_model.PROJECTSTATE_ACTIVE)},
|
||||
new: []*model.ProjectRole{
|
||||
&model.ProjectRole{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Key: "Key"},
|
||||
&model.ProjectRole{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Key: "Key2"},
|
||||
},
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
eventLen: 2,
|
||||
eventType: model.ProjectRoleAdded,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "existing project nil",
|
||||
args: args{
|
||||
@@ -753,7 +769,7 @@ func TestProjectRoleAddedAggregate(t *testing.T) {
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
agg, err := ProjectRoleAddedAggregate(tt.args.aggCreator, tt.args.existing, tt.args.new)(tt.args.ctx)
|
||||
agg, err := ProjectRoleAddedAggregate(tt.args.aggCreator, tt.args.existing, tt.args.new...)(tt.args.ctx)
|
||||
|
||||
if !tt.res.wantErr && len(agg.Events) != tt.res.eventLen {
|
||||
t.Errorf("got wrong event len: expected: %v, actual: %v ", tt.res.eventLen, len(agg.Events))
|
||||
@@ -857,13 +873,14 @@ func TestProjectRoleRemovedAggregate(t *testing.T) {
|
||||
ctx context.Context
|
||||
existing *model.Project
|
||||
new *model.ProjectRole
|
||||
grants []*model.ProjectGrant
|
||||
aggCreator *models.AggregateCreator
|
||||
}
|
||||
type res struct {
|
||||
eventLen int
|
||||
eventType models.EventType
|
||||
wantErr bool
|
||||
errFunc func(err error) bool
|
||||
eventLen int
|
||||
eventTypes []models.EventType
|
||||
wantErr bool
|
||||
errFunc func(err error) bool
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
@@ -879,8 +896,27 @@ func TestProjectRoleRemovedAggregate(t *testing.T) {
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
eventLen: 1,
|
||||
eventType: model.ProjectRoleRemoved,
|
||||
eventLen: 1,
|
||||
eventTypes: []models.EventType{model.ProjectRoleRemoved},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "projectrole changed with grant",
|
||||
args: args{
|
||||
ctx: auth.NewMockContext("orgID", "userID"),
|
||||
existing: &model.Project{
|
||||
ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"},
|
||||
Name: "ProjectName",
|
||||
State: int32(proj_model.PROJECTSTATE_ACTIVE),
|
||||
Grants: []*model.ProjectGrant{&model.ProjectGrant{ObjectRoot: models.ObjectRoot{AggregateID: "ID"}, GrantID: "GrantID", GrantedOrgID: "OrgID", RoleKeys: []string{"ROLE"}}},
|
||||
},
|
||||
new: &model.ProjectRole{ObjectRoot: models.ObjectRoot{AggregateID: "AggregateID"}, Key: "Key"},
|
||||
grants: []*model.ProjectGrant{&model.ProjectGrant{ObjectRoot: models.ObjectRoot{AggregateID: "ID"}, GrantID: "GrantID", GrantedOrgID: "OrgID", RoleKeys: []string{}}},
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
eventLen: 2,
|
||||
eventTypes: []models.EventType{model.ProjectRoleRemoved, model.ProjectGrantCascadeChanged},
|
||||
},
|
||||
},
|
||||
{
|
||||
@@ -891,10 +927,8 @@ func TestProjectRoleRemovedAggregate(t *testing.T) {
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
eventLen: 1,
|
||||
eventType: model.ProjectRoleRemoved,
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
},
|
||||
},
|
||||
{
|
||||
@@ -906,26 +940,29 @@ func TestProjectRoleRemovedAggregate(t *testing.T) {
|
||||
aggCreator: models.NewAggregateCreator("Test"),
|
||||
},
|
||||
res: res{
|
||||
eventLen: 1,
|
||||
eventType: model.ProjectRoleRemoved,
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
wantErr: true,
|
||||
errFunc: caos_errs.IsPreconditionFailed,
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
agg, err := ProjectRoleRemovedAggregate(tt.args.aggCreator, tt.args.existing, tt.args.new)(tt.args.ctx)
|
||||
agg, err := ProjectRoleRemovedAggregate(tt.args.ctx, tt.args.aggCreator, tt.args.existing, tt.args.new, tt.args.grants)
|
||||
|
||||
if !tt.res.wantErr && len(agg.Events) != tt.res.eventLen {
|
||||
t.Errorf("got wrong event len: expected: %v, actual: %v ", tt.res.eventLen, len(agg.Events))
|
||||
}
|
||||
if !tt.res.wantErr && agg.Events[0].Type != tt.res.eventType {
|
||||
t.Errorf("got wrong event type: expected: %v, actual: %v ", tt.res.eventType, agg.Events[0].Type.String())
|
||||
}
|
||||
if !tt.res.wantErr && agg.Events[0].Data == nil {
|
||||
t.Errorf("should have data in event")
|
||||
if agg != nil {
|
||||
for i, _ := range agg.Events {
|
||||
if !tt.res.wantErr && agg.Events[i].Type != tt.res.eventTypes[i] {
|
||||
t.Errorf("got wrong event type: expected: %v, actual: %v ", tt.res.eventTypes[i], agg.Events[i].Type.String())
|
||||
}
|
||||
if !tt.res.wantErr && agg.Events[i].Data == nil {
|
||||
t.Errorf("should have data in event")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if tt.res.wantErr && !tt.res.errFunc(err) {
|
||||
t.Errorf("got wrong err: %v ", err)
|
||||
}
|
||||
|
Reference in New Issue
Block a user