Skip to content

Commit

Permalink
Merge pull request #398 from sangkenlee/policytemplate-permittedorg-fix
Browse files Browse the repository at this point in the history
PolicyTemplate permittedOrganizations 수정
  • Loading branch information
ktkfree authored Apr 18, 2024
2 parents 94d0b1a + ac40063 commit 4623122
Show file tree
Hide file tree
Showing 5 changed files with 160 additions and 67 deletions.
40 changes: 33 additions & 7 deletions internal/delivery/http/policy-template.go
Original file line number Diff line number Diff line change
Expand Up @@ -261,10 +261,18 @@ func (h *PolicyTemplateHandler) Admin_GetPolicyTemplate(w http.ResponseWriter, r
log.Error(r.Context(), err)
}

if err = h.usecase.FillPermittedOrganizations(r.Context(), policyTemplate, &out.PolicyTemplate); err != nil {
log.Error(r.Context(), err)
out.PolicyTemplate.PermittedOrganizations = make([]domain.SimpleOrganizationResponse, len(policyTemplate.PermittedOrganizations))
for i, organization := range policyTemplate.PermittedOrganizations {
if err := serializer.Map(r.Context(), organization, &out.PolicyTemplate.PermittedOrganizations[i]); err != nil {
log.Info(r.Context(), err)
continue
}
}

// if err = h.usecase.FillPermittedOrganizations(r.Context(), policyTemplate, &out.PolicyTemplate); err != nil {
// log.Error(r.Context(), err)
// }

ResponseJSON(w, r, http.StatusOK, out)
}

Expand Down Expand Up @@ -301,12 +309,21 @@ func (h *PolicyTemplateHandler) Admin_ListPolicyTemplate(w http.ResponseWriter,
log.Info(r.Context(), err)
continue
}
}

if err = h.usecase.FillPermittedOrganizationsForList(r.Context(), &policyTemplates, &out.PolicyTemplates); err != nil {
log.Error(r.Context(), err)
out.PolicyTemplates[i].PermittedOrganizations = make([]domain.SimpleOrganizationResponse, len(policyTemplate.PermittedOrganizations))
for j, organization := range policyTemplate.PermittedOrganizations {
if err := serializer.Map(r.Context(), organization, &out.PolicyTemplates[i].PermittedOrganizations[j]); err != nil {
log.Info(r.Context(), err)
continue
}
}

}

// if err = h.usecase.FillPermittedOrganizationsForList(r.Context(), &policyTemplates, &out.PolicyTemplates); err != nil {
// log.Error(r.Context(), err)
// }

if out.Pagination, err = pg.Response(r.Context()); err != nil {
log.Info(r.Context(), err)
}
Expand Down Expand Up @@ -554,10 +571,19 @@ func (h *PolicyTemplateHandler) Admin_GetPolicyTemplateVersion(w http.ResponseWr
log.Error(r.Context(), err)
}

if err = h.usecase.FillPermittedOrganizations(r.Context(), policyTemplate, &out.PolicyTemplate); err != nil {
log.Error(r.Context(), err)
out.PolicyTemplate.PermittedOrganizations = make([]domain.SimpleOrganizationResponse, len(policyTemplate.PermittedOrganizations))

for i, organization := range policyTemplate.PermittedOrganizations {
if err := serializer.Map(r.Context(), organization, &out.PolicyTemplate.PermittedOrganizations[i]); err != nil {
log.Info(r.Context(), err)
continue
}
}

// if err = h.usecase.FillPermittedOrganizations(r.Context(), policyTemplate, &out.PolicyTemplate); err != nil {
// log.Error(r.Context(), err)
// }

ResponseJSON(w, r, http.StatusOK, out)
}

Expand Down
18 changes: 15 additions & 3 deletions internal/repository/policy-template.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,19 @@ func NewPolicyTemplateRepository(db *gorm.DB) IPolicyTemplateRepository {
}

func (r *PolicyTemplateRepository) Create(ctx context.Context, dto model.PolicyTemplate) (policyTemplateId uuid.UUID, err error) {
err = r.db.WithContext(ctx).Create(&dto).Error
err = r.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
// 이미 org가 존재하므로 many2many 레코드를 추가하지 않고 관계만 업데이트하도록 보장
if err := tx.Omit("PermittedOrganizations").Create(&dto).Error; err != nil {
return err
}

if err := tx.Model(&dto).Association("PermittedOrganizations").
Append(dto.PermittedOrganizations); err != nil {
return err
}

return nil
})

if err != nil {
return uuid.Nil, err
Expand All @@ -67,7 +79,7 @@ func (r *PolicyTemplateRepository) Update(ctx context.Context, policyTemplateId

return r.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
if permittedOrganizations != nil {
err = r.db.WithContext(ctx).Model(&policyTemplate).Limit(1).
err = tx.WithContext(ctx).Model(&policyTemplate).Limit(1).
Association("PermittedOrganizations").Replace(permittedOrganizations)

if err != nil {
Expand All @@ -76,7 +88,7 @@ func (r *PolicyTemplateRepository) Update(ctx context.Context, policyTemplateId
}

if len(updateMap) > 0 {
err = r.db.WithContext(ctx).Model(&policyTemplate).Limit(1).
err = tx.WithContext(ctx).Model(&policyTemplate).Limit(1).
Where("id = ?", policyTemplateId).Where("type = ?", "tks").
Updates(updateMap).Error

Expand Down
14 changes: 13 additions & 1 deletion internal/repository/policy.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,19 @@ func NewPolicyRepository(db *gorm.DB) IPolicyRepository {
}

func (r *PolicyRepository) Create(ctx context.Context, dto model.Policy) (policyId uuid.UUID, err error) {
err = r.db.WithContext(ctx).Create(&dto).Error
err = r.db.WithContext(ctx).Transaction(func(tx *gorm.DB) error {
// 이미 org가 존재하므로 many2many 레코드를 추가하지 않고 관계만 업데이트하도록 보장
if err := tx.Omit("TargetClusters").Create(&dto).Error; err != nil {
return err
}

if err := tx.Model(&dto).Association("TargetClusters").
Append(dto.TargetClusters); err != nil {
return err
}

return nil
})

if err != nil {
return uuid.Nil, err
Expand Down
143 changes: 93 additions & 50 deletions internal/usecase/policy-template.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,8 @@ import (
"fmt"
"strings"

admin_domain "github.com/openinfradev/tks-api/pkg/domain/admin"
"github.com/openinfradev/tks-api/pkg/log"

mapset "github.com/deckarep/golang-set/v2"
"github.com/google/uuid"
"github.com/openinfradev/tks-api/internal/middleware/auth/request"
"github.com/openinfradev/tks-api/internal/model"
Expand All @@ -35,10 +33,10 @@ type IPolicyTemplateUsecase interface {

RegoCompile(request *domain.RegoCompileRequest, parseParameter bool) (response *domain.RegoCompileResponse, err error)

FillPermittedOrganizations(ctx context.Context,
policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) error
FillPermittedOrganizationsForList(ctx context.Context,
policyTemplates *[]model.PolicyTemplate, outs *[]admin_domain.PolicyTemplateResponse) error
// FillPermittedOrganizations(ctx context.Context,
// policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) error
// FillPermittedOrganizationsForList(ctx context.Context,
// policyTemplates *[]model.PolicyTemplate, outs *[]admin_domain.PolicyTemplateResponse) error

ListPolicyTemplateStatistics(ctx context.Context, organizationId *string, policyTemplateId uuid.UUID) (statistics []model.UsageCount, err error)
GetPolicyTemplateDeploy(ctx context.Context, organizationId *string, policyTemplateId uuid.UUID) (deployInfo domain.GetPolicyTemplateDeployResponse, err error)
Expand Down Expand Up @@ -102,15 +100,18 @@ func (u *PolicyTemplateUsecase) Create(ctx context.Context, dto model.PolicyTemp
// TKS 템블릿이면
dto.Mandatory = false
dto.OrganizationId = nil
dto.PermittedOrganizations = make([]model.Organization, len(dto.PermittedOrganizationIds))

for _, organizationId := range dto.PermittedOrganizationIds {
_, err := u.organizationRepo.Get(ctx, organizationId)
for i, organizationId := range dto.PermittedOrganizationIds {
organization, err := u.organizationRepo.Get(ctx, organizationId)
if err != nil {
return uuid.Nil, httpErrors.NewBadRequestError(fmt.Errorf("invalid organizationId"), "C_INVALID_ORGANIZATION_ID", "")
}
dto.PermittedOrganizations[i] = organization
}
} else {
dto.PermittedOrganizationIds = make([]string, 0)
dto.PermittedOrganizations = make([]model.Organization, 0)
}

userId := user.GetUserId()
Expand All @@ -127,71 +128,93 @@ func (u *PolicyTemplateUsecase) Create(ctx context.Context, dto model.PolicyTemp

func (u *PolicyTemplateUsecase) Fetch(ctx context.Context, organizationId *string, pg *pagination.Pagination) (policyTemplates []model.PolicyTemplate, err error) {
if organizationId == nil {
return u.repo.Fetch(ctx, pg)
policyTemplates, err = u.repo.Fetch(ctx, pg)
} else {
policyTemplates, err = u.repo.FetchForOrganization(ctx, *organizationId, pg)
}

return u.repo.FetchForOrganization(ctx, *organizationId, pg)
}
if err != nil {
log.Errorf(ctx, "error is :%s(%T)", err.Error(), err)
}

func (u *PolicyTemplateUsecase) FillPermittedOrganizations(ctx context.Context,
policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) error {
organizations, err := u.organizationRepo.Fetch(ctx, nil)

if err != nil {
return err
log.Errorf(ctx, "error is :%s(%T)", err.Error(), err)
}

u.fillPermittedOrganizations(ctx, organizations, policyTemplate, out)
for i := range policyTemplates {
// 단순히 참조하면 업데이트가 안되므로 pointer derefrencing
policyTemplate := &policyTemplates[i]
if policyTemplate.IsTksTemplate() && len(policyTemplate.PermittedOrganizations) == 0 {
if organizations != nil {
(*policyTemplate).PermittedOrganizations = *organizations
}
}
}

return nil
return policyTemplates, err
}

func (u *PolicyTemplateUsecase) FillPermittedOrganizationsForList(ctx context.Context,
policyTemplates *[]model.PolicyTemplate, outs *[]admin_domain.PolicyTemplateResponse) error {
// func (u *PolicyTemplateUsecase) FillPermittedOrganizations(ctx context.Context,
// policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) error {
// organizations, err := u.organizationRepo.Fetch(ctx, nil)

organizations, err := u.organizationRepo.Fetch(ctx, nil)
// if err != nil {
// return err
// }

if err != nil {
return err
}
// u.fillPermittedOrganizations(ctx, organizations, policyTemplate, out)

results := *outs
// return nil
// }

for i, policyTemplate := range *policyTemplates {
u.fillPermittedOrganizations(ctx, organizations, &policyTemplate, &results[i])
}
// func (u *PolicyTemplateUsecase) FillPermittedOrganizationsForList(ctx context.Context,
// policyTemplates *[]model.PolicyTemplate, outs *[]admin_domain.PolicyTemplateResponse) error {

return nil
}
// organizations, err := u.organizationRepo.Fetch(ctx, nil)

// 모든 조직 목록에 대해 허용 여부 업데이트
func (u *PolicyTemplateUsecase) fillPermittedOrganizations(_ context.Context, organizations *[]model.Organization, policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) {
if policyTemplate == nil || organizations == nil || out == nil {
return
}
// if err != nil {
// return err
// }

if policyTemplate.IsOrganizationTemplate() {
return
}
// results := *outs

// 정책 템플릿에서 허용된 조직 목록이 없다는 것은 모든 조직이 사용할 수 있음을 의미함
allPermitted := len(policyTemplate.PermittedOrganizationIds) == 0
// for i, policyTemplate := range *policyTemplates {
// u.fillPermittedOrganizations(ctx, organizations, &policyTemplate, &results[i])
// }

// 허용된 조직 포함 여부를 효율적으로 처리하기 위해 ID 리스트를 셋으로 변환
permittedOrganizationIdSet := mapset.NewSet(policyTemplate.PermittedOrganizationIds...)
// return nil
// }

out.PermittedOrganizations = make([]admin_domain.PermittedOrganization, len(*organizations))
// // 모든 조직 목록에 대해 허용 여부 업데이트
// func (u *PolicyTemplateUsecase) fillPermittedOrganizations(_ context.Context, organizations *[]model.Organization, policyTemplate *model.PolicyTemplate, out *admin_domain.PolicyTemplateResponse) {
// if policyTemplate == nil || organizations == nil || out == nil {
// return
// }

for i, organization := range *organizations {
permitted := allPermitted || permittedOrganizationIdSet.ContainsOne(organization.ID)
// if policyTemplate.IsOrganizationTemplate() {
// return
// }

out.PermittedOrganizations[i] = admin_domain.PermittedOrganization{
OrganizationId: organization.ID,
OrganizationName: organization.Name,
Permitted: permitted,
}
}
}
// // 정책 템플릿에서 허용된 조직 목록이 없다는 것은 모든 조직이 사용할 수 있음을 의미함
// allPermitted := len(policyTemplate.PermittedOrganizationIds) == 0

// // 허용된 조직 포함 여부를 효율적으로 처리하기 위해 ID 리스트를 셋으로 변환
// permittedOrganizationIdSet := mapset.NewSet(policyTemplate.PermittedOrganizationIds...)

// out.PermittedOrganizations = make([]admin_domain.PermittedOrganization, len(*organizations))

// for i, organization := range *organizations {
// permitted := allPermitted || permittedOrganizationIdSet.ContainsOne(organization.ID)

// out.PermittedOrganizations[i] = admin_domain.PermittedOrganization{
// OrganizationId: organization.ID,
// OrganizationName: organization.Name,
// Permitted: permitted,
// }
// }
// }

func (u *PolicyTemplateUsecase) Get(ctx context.Context, organizationId *string, policyTemplateID uuid.UUID) (policyTemplates *model.PolicyTemplate, err error) {
policyTemplate, err := u.repo.GetByID(ctx, policyTemplateID)
Expand All @@ -206,6 +229,16 @@ func (u *PolicyTemplateUsecase) Get(ctx context.Context, organizationId *string,
"PT_NOT_FOUND_POLICY_TEMPLATE", "")
}

if policyTemplate.IsTksTemplate() && len(policyTemplate.PermittedOrganizations) == 0 {
organizations, err := u.organizationRepo.Fetch(ctx, nil)

if err != nil {
log.Errorf(ctx, "error is :%s(%T)", err.Error(), err)
} else if organizations != nil {
policyTemplate.PermittedOrganizations = *organizations
}
}

return policyTemplate, nil
}

Expand Down Expand Up @@ -357,6 +390,16 @@ func (u *PolicyTemplateUsecase) GetPolicyTemplateVersion(ctx context.Context, or
"PT_NOT_FOUND_POLICY_TEMPLATE", "")
}

if policyTemplate.IsTksTemplate() && len(policyTemplate.PermittedOrganizations) == 0 {
organizations, err := u.organizationRepo.Fetch(ctx, nil)

if err != nil {
log.Errorf(ctx, "error is :%s(%T)", err.Error(), err)
} else if organizations != nil {
policyTemplate.PermittedOrganizations = *organizations
}
}

return policyTemplate, nil
}

Expand Down
12 changes: 6 additions & 6 deletions pkg/domain/admin/policy-template.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,11 @@ import (
"github.com/openinfradev/tks-api/pkg/domain"
)

type PermittedOrganization struct {
OrganizationId string `json:"organizationId"`
OrganizationName string `json:"organizationName"`
Permitted bool `json:"permitted"`
}
// type PermittedOrganization struct {
// OrganizationId string `json:"organizationId"`
// OrganizationName string `json:"organizationName"`
// Permitted bool `json:"permitted"`
// }

type PolicyTemplateResponse struct {
ID string `json:"id" example:"d98ef5f1-4a68-4047-a446-2207787ce3ff"`
Expand All @@ -30,7 +30,7 @@ type PolicyTemplateResponse struct {
Rego string `json:"rego" example:"rego 코드"`
Libs []string `json:"libs" example:"rego 코드"`

PermittedOrganizations []PermittedOrganization `json:"permittedOrganizations"`
PermittedOrganizations []domain.SimpleOrganizationResponse `json:"permittedOrganizations"`
}

type SimplePolicyTemplateResponse struct {
Expand Down

0 comments on commit 4623122

Please sign in to comment.