Team Guardian: Refactor it to remove the bus dependency (#43058)
* Refactor team guardian to avoid to use bus * Fix lint * Fix lint
This commit is contained in:
@@ -0,0 +1,22 @@
|
||||
package database
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
"github.com/grafana/grafana/pkg/services/sqlstore"
|
||||
)
|
||||
|
||||
type TeamGuardianStoreImpl struct{}
|
||||
|
||||
func ProvideTeamGuardianStore() *TeamGuardianStoreImpl {
|
||||
return &TeamGuardianStoreImpl{}
|
||||
}
|
||||
|
||||
func (t *TeamGuardianStoreImpl) GetTeamMembers(ctx context.Context, query models.GetTeamMembersQuery) ([]*models.TeamMemberDTO, error) {
|
||||
if err := sqlstore.GetTeamMembers(ctx, &query); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return query.Result, nil
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package database
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
"github.com/stretchr/testify/mock"
|
||||
)
|
||||
|
||||
type TeamGuardianStoreMock struct {
|
||||
mock.Mock
|
||||
}
|
||||
|
||||
func (t *TeamGuardianStoreMock) GetTeamMembers(ctx context.Context, query models.GetTeamMembersQuery) ([]*models.TeamMemberDTO, error) {
|
||||
args := t.Called(ctx, query)
|
||||
return args.Get(0).([]*models.TeamMemberDTO), args.Error(1)
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
package manager
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
"github.com/grafana/grafana/pkg/services/teamguardian"
|
||||
)
|
||||
|
||||
type Service struct {
|
||||
store teamguardian.Store
|
||||
}
|
||||
|
||||
func ProvideService(store teamguardian.Store) *Service {
|
||||
return &Service{store: store}
|
||||
}
|
||||
|
||||
func (s *Service) CanAdmin(ctx context.Context, orgId int64, teamId int64, user *models.SignedInUser) error {
|
||||
if user.OrgRole == models.ROLE_ADMIN {
|
||||
return nil
|
||||
}
|
||||
|
||||
if user.OrgId != orgId {
|
||||
return models.ErrNotAllowedToUpdateTeamInDifferentOrg
|
||||
}
|
||||
|
||||
cmd := models.GetTeamMembersQuery{
|
||||
OrgId: orgId,
|
||||
TeamId: teamId,
|
||||
UserId: user.UserId,
|
||||
}
|
||||
|
||||
results, err := s.store.GetTeamMembers(ctx, cmd)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, member := range results {
|
||||
if member.UserId == user.UserId && member.Permission == models.PERMISSION_ADMIN {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
return models.ErrNotAllowedToUpdateTeam
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package manager
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
"github.com/stretchr/testify/mock"
|
||||
)
|
||||
|
||||
type TeamGuardianMock struct {
|
||||
mock.Mock
|
||||
}
|
||||
|
||||
func (t *TeamGuardianMock) CanAdmin(ctx context.Context, orgId int64, teamId int64, user *models.SignedInUser) error {
|
||||
args := t.Called(ctx, orgId, teamId, user)
|
||||
return args.Error(0)
|
||||
}
|
||||
+30
-32
@@ -1,19 +1,20 @@
|
||||
package teamguardian
|
||||
package manager
|
||||
|
||||
import (
|
||||
"context"
|
||||
"testing"
|
||||
|
||||
"github.com/grafana/grafana/pkg/bus"
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
|
||||
"github.com/grafana/grafana/pkg/services/teamguardian/database"
|
||||
"github.com/stretchr/testify/mock"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func TestUpdateTeam(t *testing.T) {
|
||||
t.Run("Updating a team", func(t *testing.T) {
|
||||
bus.ClearBusHandlers()
|
||||
store := new(database.TeamGuardianStoreMock)
|
||||
teamGuardianService := ProvideService(store)
|
||||
|
||||
t.Run("Updating a team", func(t *testing.T) {
|
||||
admin := models.SignedInUser{
|
||||
UserId: 1,
|
||||
OrgId: 1,
|
||||
@@ -31,58 +32,55 @@ func TestUpdateTeam(t *testing.T) {
|
||||
|
||||
t.Run("Given an editor and a team he isn't a member of", func(t *testing.T) {
|
||||
t.Run("Should not be able to update the team", func(t *testing.T) {
|
||||
bus.AddHandler("test", func(ctx context.Context, cmd *models.GetTeamMembersQuery) error {
|
||||
cmd.Result = []*models.TeamMemberDTO{}
|
||||
return nil
|
||||
})
|
||||
|
||||
err := CanAdmin(context.Background(), bus.GetBus(), testTeam.OrgId, testTeam.Id, &editor)
|
||||
ctx := context.Background()
|
||||
store.On("GetTeamMembers", ctx, mock.Anything).Return([]*models.TeamMemberDTO{}, nil).Once()
|
||||
err := teamGuardianService.CanAdmin(ctx, testTeam.OrgId, testTeam.Id, &editor)
|
||||
require.Equal(t, models.ErrNotAllowedToUpdateTeam, err)
|
||||
})
|
||||
})
|
||||
|
||||
t.Run("Given an editor and a team he is an admin in", func(t *testing.T) {
|
||||
t.Run("Should be able to update the team", func(t *testing.T) {
|
||||
bus.AddHandler("test", func(ctx context.Context, cmd *models.GetTeamMembersQuery) error {
|
||||
cmd.Result = []*models.TeamMemberDTO{{
|
||||
OrgId: testTeam.OrgId,
|
||||
TeamId: testTeam.Id,
|
||||
UserId: editor.UserId,
|
||||
Permission: models.PERMISSION_ADMIN,
|
||||
}}
|
||||
return nil
|
||||
})
|
||||
ctx := context.Background()
|
||||
|
||||
err := CanAdmin(context.Background(), bus.GetBus(), testTeam.OrgId, testTeam.Id, &editor)
|
||||
result := []*models.TeamMemberDTO{{
|
||||
OrgId: testTeam.OrgId,
|
||||
TeamId: testTeam.Id,
|
||||
UserId: editor.UserId,
|
||||
Permission: models.PERMISSION_ADMIN,
|
||||
}}
|
||||
|
||||
store.On("GetTeamMembers", ctx, mock.Anything).Return(result, nil).Once()
|
||||
err := teamGuardianService.CanAdmin(ctx, testTeam.OrgId, testTeam.Id, &editor)
|
||||
require.NoError(t, err)
|
||||
})
|
||||
})
|
||||
|
||||
t.Run("Given an editor and a team in another org", func(t *testing.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
testTeamOtherOrg := models.Team{
|
||||
Id: 1,
|
||||
OrgId: 2,
|
||||
}
|
||||
|
||||
t.Run("Shouldn't be able to update the team", func(t *testing.T) {
|
||||
bus.AddHandler("test", func(ctx context.Context, cmd *models.GetTeamMembersQuery) error {
|
||||
cmd.Result = []*models.TeamMemberDTO{{
|
||||
OrgId: testTeamOtherOrg.OrgId,
|
||||
TeamId: testTeamOtherOrg.Id,
|
||||
UserId: editor.UserId,
|
||||
Permission: models.PERMISSION_ADMIN,
|
||||
}}
|
||||
return nil
|
||||
})
|
||||
result := []*models.TeamMemberDTO{{
|
||||
OrgId: testTeamOtherOrg.OrgId,
|
||||
TeamId: testTeamOtherOrg.Id,
|
||||
UserId: editor.UserId,
|
||||
Permission: models.PERMISSION_ADMIN,
|
||||
}}
|
||||
|
||||
err := CanAdmin(context.Background(), bus.GetBus(), testTeamOtherOrg.OrgId, testTeamOtherOrg.Id, &editor)
|
||||
store.On("GetTeamMembers", ctx, mock.Anything).Return(result, nil).Once()
|
||||
err := teamGuardianService.CanAdmin(ctx, testTeamOtherOrg.OrgId, testTeamOtherOrg.Id, &editor)
|
||||
require.Equal(t, models.ErrNotAllowedToUpdateTeamInDifferentOrg, err)
|
||||
})
|
||||
})
|
||||
|
||||
t.Run("Given an org admin and a team", func(t *testing.T) {
|
||||
t.Run("Should be able to update the team", func(t *testing.T) {
|
||||
err := CanAdmin(context.Background(), bus.GetBus(), testTeam.OrgId, testTeam.Id, &admin)
|
||||
err := teamGuardianService.CanAdmin(context.Background(), testTeam.OrgId, testTeam.Id, &admin)
|
||||
require.NoError(t, err)
|
||||
})
|
||||
})
|
||||
@@ -3,34 +3,13 @@ package teamguardian
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/grafana/grafana/pkg/bus"
|
||||
"github.com/grafana/grafana/pkg/models"
|
||||
)
|
||||
|
||||
func CanAdmin(ctx context.Context, bus bus.Bus, orgId int64, teamId int64, user *models.SignedInUser) error {
|
||||
if user.OrgRole == models.ROLE_ADMIN {
|
||||
return nil
|
||||
}
|
||||
type TeamGuardian interface {
|
||||
CanAdmin(ctx context.Context, orgId int64, teamId int64, user *models.SignedInUser) error
|
||||
}
|
||||
|
||||
if user.OrgId != orgId {
|
||||
return models.ErrNotAllowedToUpdateTeamInDifferentOrg
|
||||
}
|
||||
|
||||
cmd := models.GetTeamMembersQuery{
|
||||
OrgId: orgId,
|
||||
TeamId: teamId,
|
||||
UserId: user.UserId,
|
||||
}
|
||||
|
||||
if err := bus.Dispatch(ctx, &cmd); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, member := range cmd.Result {
|
||||
if member.UserId == user.UserId && member.Permission == models.PERMISSION_ADMIN {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
return models.ErrNotAllowedToUpdateTeam
|
||||
type Store interface {
|
||||
GetTeamMembers(ctx context.Context, query models.GetTeamMembersQuery) ([]*models.TeamMemberDTO, error)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user