summaryrefslogtreecommitdiffstats
path: root/app/email.go
diff options
context:
space:
mode:
authorChristopher Speller <crspeller@gmail.com>2018-07-10 01:54:25 -0700
committerCarlos Tadeu Panato Junior <ctadeu@gmail.com>2018-07-10 10:54:25 +0200
commit74e5d8ae66186a82e8afdd845a108d6a662751d7 (patch)
treefaeeee70a251b636bae0afb4e60c611e00c2cc6b /app/email.go
parent951e4ad98401e9828b9941224318f105fb15d500 (diff)
downloadchat-74e5d8ae66186a82e8afdd845a108d6a662751d7.tar.gz
chat-74e5d8ae66186a82e8afdd845a108d6a662751d7.tar.bz2
chat-74e5d8ae66186a82e8afdd845a108d6a662751d7.zip
MM-11120 Adding setting to disable email invitations and rate limiting. (#9063)
* Adding setting to disable email invitations. * Adding a setting and rate limiting for email invite sending. * Modifying email rate limit to 20/user/hour * Adding EnableEmailInvitations to client side config and command.
Diffstat (limited to 'app/email.go')
-rw-r--r--app/email.go48
1 files changed, 47 insertions, 1 deletions
diff --git a/app/email.go b/app/email.go
index b4e0a8983..569e6f454 100644
--- a/app/email.go
+++ b/app/email.go
@@ -10,12 +10,41 @@ import (
"net/http"
"github.com/nicksnyder/go-i18n/i18n"
+ "github.com/pkg/errors"
+ "github.com/throttled/throttled"
+ "github.com/throttled/throttled/store/memstore"
"github.com/mattermost/mattermost-server/mlog"
"github.com/mattermost/mattermost-server/model"
"github.com/mattermost/mattermost-server/utils"
)
+const (
+ emailRateLimitingMemstoreSize = 65536
+ emailRateLimitingPerHour = 20
+ emailRateLimitingMaxBurst = 20
+)
+
+func (a *App) SetupInviteEmailRateLimiting() error {
+ store, err := memstore.New(emailRateLimitingMemstoreSize)
+ if err != nil {
+ return errors.Wrap(err, "Unable to setup email rate limiting memstore.")
+ }
+
+ quota := throttled.RateQuota{
+ MaxRate: throttled.PerHour(emailRateLimitingPerHour),
+ MaxBurst: emailRateLimitingMaxBurst,
+ }
+
+ rateLimiter, err := throttled.NewGCRARateLimiter(store, quota)
+ if err != nil || rateLimiter == nil {
+ return errors.Wrap(err, "Unable to setup email rate limiting GCRA rate limiter.")
+ }
+
+ a.EmailRateLimiter = rateLimiter
+ return nil
+}
+
func (a *App) SendChangeUsernameEmail(oldUsername, newUsername, email, locale, siteURL string) *model.AppError {
T := utils.GetUserTranslations(locale)
@@ -247,7 +276,24 @@ func (a *App) SendMfaChangeEmail(email string, activated bool, locale, siteURL s
return nil
}
-func (a *App) SendInviteEmails(team *model.Team, senderName string, invites []string, siteURL string) {
+func (a *App) SendInviteEmails(team *model.Team, senderName string, senderUserId string, invites []string, siteURL string) {
+ if a.EmailRateLimiter == nil {
+ a.Log.Error("Email invite not sent, rate limiting could not be setup.", mlog.String("user_id", senderUserId), mlog.String("team_id", team.Id))
+ return
+ }
+ rateLimited, result, err := a.EmailRateLimiter.RateLimit(senderUserId, len(invites))
+ if rateLimited {
+ a.Log.Error("Invite emails rate limited.",
+ mlog.String("user_id", senderUserId),
+ mlog.String("team_id", team.Id),
+ mlog.String("retry_after", result.RetryAfter.String()),
+ mlog.Err(err))
+ return
+ } else if err != nil {
+ a.Log.Error("Error rate limiting invite email.", mlog.String("user_id", senderUserId), mlog.String("team_id", team.Id), mlog.Err(err))
+ return
+ }
+
for _, invite := range invites {
if len(invite) > 0 {
senderRole := utils.T("api.team.invite_members.member")