diff --git a/server/api.go b/server/api.go index 68b0af8..66b1793 100644 --- a/server/api.go +++ b/server/api.go @@ -421,7 +421,15 @@ func (p *Plugin) apiUpdateBadge(w http.ResponseWriter, r *http.Request, userID s return } - if !canEditBadge(user, p.badgeAdminUserIDs, badge) { + badgeType, err := p.store.GetType(badge.Type) + if err != nil { + p.writeAPIError(w, &APIErrorResponse{ + ID: "type_not_found", Message: "Badge type not found", StatusCode: http.StatusInternalServerError, + }) + return + } + + if !canEditBadge(user, p.badgeAdminUserIDs, badge, badgeType) { p.writeAPIError(w, &APIErrorResponse{ ID: "no_permission", Message: "No permission to edit this badge", StatusCode: http.StatusForbidden, }) @@ -564,7 +572,15 @@ func (p *Plugin) apiDeleteBadge(w http.ResponseWriter, r *http.Request, userID s return } - if !canEditBadge(user, p.badgeAdminUserIDs, badge) { + badgeType, err := p.store.GetType(badge.Type) + if err != nil { + p.writeAPIError(w, &APIErrorResponse{ + ID: "type_not_found", Message: "Badge type not found", StatusCode: http.StatusInternalServerError, + }) + return + } + + if !canEditBadge(user, p.badgeAdminUserIDs, badge, badgeType) { p.writeAPIError(w, &APIErrorResponse{ ID: "no_permission", Message: "No permission to delete this badge", StatusCode: http.StatusForbidden, }) @@ -972,7 +988,13 @@ func (p *Plugin) dialogSelectBadge(w http.ResponseWriter, r *http.Request, userI } T := p.getT(u.Locale) - if !canEditBadge(u, p.badgeAdminUserIDs, b) { + bt, err := p.store.GetType(b.Type) + if err != nil { + dialogError(w, T("badges.api.cannot_get_type", "Не удалось получить тип значка"), nil) + return + } + + if !canEditBadge(u, p.badgeAdminUserIDs, b, bt) { dialogError(w, T("badges.api.cannot_edit_badge", "Вы не можете редактировать этот значок"), nil) return } @@ -1011,7 +1033,13 @@ func (p *Plugin) dialogEditBadge(w http.ResponseWriter, r *http.Request, userID return } - if !canEditBadge(u, p.badgeAdminUserIDs, originalBadge) { + originalBadgeType, err := p.store.GetType(originalBadge.Type) + if err != nil { + dialogError(w, T("badges.api.cannot_get_type", "Не удалось получить тип значка"), nil) + return + } + + if !canEditBadge(u, p.badgeAdminUserIDs, originalBadge, originalBadgeType) { dialogError(w, T("badges.api.no_permissions_edit_badge", "У вас нет прав на редактирование этого значка"), nil) return } @@ -1529,7 +1557,23 @@ func (p *Plugin) getBadgeDetails(w http.ResponseWriter, r *http.Request, actingU p.mm.Log.Debug("Cannot get badge details", "badgeID", badgeID, "error", err) } - b, _ := json.Marshal(badge) + type BadgeDetailsResponse struct { + *badgesmodel.BadgeDetails + CanEdit bool `json:"can_edit"` + } + + resp := BadgeDetailsResponse{BadgeDetails: badge} + if badge != nil { + actingUser, userErr := p.mm.User.Get(actingUserID) + if userErr == nil { + bt, typeErr := p.store.GetType(badge.Type) + if typeErr == nil { + resp.CanEdit = canEditBadge(actingUser, p.badgeAdminUserIDs, &badge.Badge, bt) + } + } + } + + b, _ := json.Marshal(resp) _, _ = w.Write(b) } diff --git a/server/command.go b/server/command.go index 66d596e..d0c312a 100644 --- a/server/command.go +++ b/server/command.go @@ -271,7 +271,12 @@ func (p *Plugin) runEditBadge(args []string, extra *model.CommandArgs) (bool, *m return commandError(err.Error()) } - if !canEditBadge(u, p.badgeAdminUserIDs, badge) { + badgeType, err := p.store.GetType(badge.Type) + if err != nil { + return commandError(err.Error()) + } + + if !canEditBadge(u, p.badgeAdminUserIDs, badge, badgeType) { return commandError(T("badges.error.cannot_edit_badge", "У вас нет прав на редактирование этого значка")) } diff --git a/server/suggestions.go b/server/suggestions.go index 535bccc..5715f6f 100644 --- a/server/suggestions.go +++ b/server/suggestions.go @@ -69,9 +69,18 @@ func (p *Plugin) filterEditBadges(user *model.User) ([]*badgesmodel.Badge, error return nil, err } + typeCache := map[badgesmodel.BadgeType]*badgesmodel.BadgeTypeDefinition{} out := []*badgesmodel.Badge{} for _, b := range bb { - if canEditBadge(user, p.badgeAdminUserIDs, b) { + bt, ok := typeCache[b.Type] + if !ok { + bt, err = p.store.GetType(b.Type) + if err != nil { + continue + } + typeCache[b.Type] = bt + } + if canEditBadge(user, p.badgeAdminUserIDs, b, bt) { out = append(out, b) } } diff --git a/server/utils.go b/server/utils.go index 758556f..56b284d 100644 --- a/server/utils.go +++ b/server/utils.go @@ -96,12 +96,20 @@ func canEditType(user *model.User, badgeAdminIDs map[string]bool, badgeType *bad return user.IsSystemAdmin() } -func canEditBadge(user *model.User, badgeAdminIDs map[string]bool, badge *badgesmodel.Badge) bool { +func canEditBadge(user *model.User, badgeAdminIDs map[string]bool, badge *badgesmodel.Badge, badgeType *badgesmodel.BadgeTypeDefinition) bool { if badgeAdminIDs[user.Id] { return true } - return user.IsSystemAdmin() || user.Id == badge.CreatedBy + if user.IsSystemAdmin() { + return true + } + + if badgeType != nil && canCreateBadge(user, badgeAdminIDs, badgeType) { + return true + } + + return false } func canCreateType(user *model.User, badgeAdminIDs map[string]bool, isPlugin bool) bool { diff --git a/webapp/src/components/rhs/badge_details.tsx b/webapp/src/components/rhs/badge_details.tsx index 0549488..1dba482 100644 --- a/webapp/src/components/rhs/badge_details.tsx +++ b/webapp/src/components/rhs/badge_details.tsx @@ -179,7 +179,7 @@ class BadgeDetailsComponent extends React.PureComponent { /> - {badge.created_by === this.props.currentUserID && ( + {badge.can_edit && (