[MM-27535] User invite limits for MM Cloud (#15197)

* Add a config for MM User Limit

* Adding graceful errors for if an administrator invites people passed their user limit

* Including changed vendor files

* Adding unit test

* Fix a bug

* Push up working tests (Thanks Joram)

* Add more cases, clean up logs in code

* One more case

* Refactoring based on PR comments

* Updating i18n

* Some changes based on PR review

* Remove a comment

* Bring back some translations that were somehow removed

Co-authored-by: Mattermod <mattermod@users.noreply.github.com>
Этот коммит содержится в:
nickmisasi
2020-08-19 16:01:07 -04:00
коммит произвёл GitHub
родитель 4e154756bd
Коммит 769f39eee5
20 изменённых файлов: 452 добавлений и 156 удалений

Просмотреть файл

@@ -537,6 +537,7 @@ type AppIface interface {
GetEmojiByName(emojiName string) (*model.Emoji, *model.AppError)
GetEmojiImage(emojiId string) ([]byte, string, *model.AppError)
GetEmojiList(page, perPage int, sort string) ([]*model.Emoji, *model.AppError)
GetErrorListForEmailsOverLimit(emailList []string, cloudUserLimit int64) ([]string, []*model.EmailInviteWithError, *model.AppError)
GetFile(fileId string) ([]byte, *model.AppError)
GetFileInfo(fileId string) (*model.FileInfo, *model.AppError)
GetFileInfos(page, perPage int, opt *model.GetFileInfosOptions) ([]*model.FileInfo, *model.AppError)

Просмотреть файл

@@ -5069,6 +5069,28 @@ func (a *OpenTracingAppLayer) GetEnvironmentConfig() map[string]interface{} {
return resultVar0
}
func (a *OpenTracingAppLayer) GetErrorListForEmailsOverLimit(emailList []string, cloudUserLimit int64) ([]string, []*model.EmailInviteWithError, *model.AppError) {
origCtx := a.ctx
span, newCtx := tracing.StartSpanWithParentByContext(a.ctx, "app.GetErrorListForEmailsOverLimit")
a.ctx = newCtx
a.app.Srv().Store.SetContext(newCtx)
defer func() {
a.app.Srv().Store.SetContext(origCtx)
a.ctx = origCtx
}()
defer span.Finish()
resultVar0, resultVar1, resultVar2 := a.app.GetErrorListForEmailsOverLimit(emailList, cloudUserLimit)
if resultVar2 != nil {
span.LogFields(spanlog.Error(resultVar2))
ext.Error.Set(span, true)
}
return resultVar0, resultVar1, resultVar2
}
func (a *OpenTracingAppLayer) GetFile(fileId string) ([]byte, *model.AppError) {
origCtx := a.ctx
span, newCtx := tracing.StartSpanWithParentByContext(a.ctx, "app.GetFile")

Просмотреть файл

@@ -1127,6 +1127,47 @@ func (a *App) prepareInviteNewUsersToTeam(teamId, senderId string) (*model.User,
return user, team, nil
}
func genEmailInviteWithErrorList(emailList []string) []*model.EmailInviteWithError {
invitesNotSent := make([]*model.EmailInviteWithError, len(emailList))
for i := range emailList {
invite := &model.EmailInviteWithError{
Email: emailList[i],
Error: model.NewAppError("inviteUsersToTeam", "api.team.invite_members.limit_reached.app_error", map[string]interface{}{"Addresses": emailList[i]}, "", http.StatusBadRequest),
}
invitesNotSent[i] = invite
}
return invitesNotSent
}
func (a *App) GetErrorListForEmailsOverLimit(emailList []string, cloudUserLimit int64) ([]string, []*model.EmailInviteWithError, *model.AppError) {
var invitesNotSent []*model.EmailInviteWithError
if cloudUserLimit <= 0 {
return emailList, invitesNotSent, nil
}
systemUserCount, _ := a.Srv().Store.User().Count(model.UserCountOptions{})
remainingUsers := cloudUserLimit - systemUserCount
if remainingUsers <= 0 {
// No remaining users so all fail
invitesNotSent = genEmailInviteWithErrorList(emailList)
emailList = nil
} else if remainingUsers < int64(len(emailList)) {
// Trim the email list to only invite as many users as are remaining in subscription
// Set graceful errors for the remaining email addresses
emailsAboveLimit := emailList[remainingUsers:]
invitesNotSent = genEmailInviteWithErrorList(emailsAboveLimit)
// If 1 user remaining we have to prevent 0:0 reslicing
if remainingUsers == 1 {
email := emailList[0]
emailList = nil
emailList = append(emailList, email)
} else {
emailList = emailList[:(remainingUsers - 1)]
}
}
return emailList, invitesNotSent, nil
}
func (a *App) InviteNewUsersToTeamGracefully(emailList []string, teamId, senderId string) ([]*model.EmailInviteWithError, *model.AppError) {
if !*a.Config().ServiceSettings.EnableEmailInvitations {
return nil, model.NewAppError("InviteNewUsersToTeam", "api.team.invite_members.disabled.app_error", nil, "", http.StatusNotImplemented)
@@ -1136,7 +1177,6 @@ func (a *App) InviteNewUsersToTeamGracefully(emailList []string, teamId, senderI
err := model.NewAppError("InviteNewUsersToTeam", "api.team.invite_members.no_one.app_error", nil, "", http.StatusBadRequest)
return nil, err
}
user, team, err := a.prepareInviteNewUsersToTeam(teamId, senderId)
if err != nil {
return nil, err