summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--custom/conf/app.example.ini2
-rw-r--r--docs/content/doc/advanced/config-cheat-sheet.en-us.md1
-rw-r--r--docs/content/doc/help/faq.en-us.md11
-rw-r--r--modules/forms/user_form.go31
-rw-r--r--modules/forms/user_form_test.go34
-rw-r--r--modules/setting/service.go2
-rw-r--r--routers/user/auth.go2
7 files changed, 61 insertions, 22 deletions
diff --git a/custom/conf/app.example.ini b/custom/conf/app.example.ini
index 276b3cb5e8..a6965c2cf6 100644
--- a/custom/conf/app.example.ini
+++ b/custom/conf/app.example.ini
@@ -617,6 +617,8 @@ REGISTER_MANUAL_CONFIRM = false
; List of domain names that are allowed to be used to register on a Gitea instance
; gitea.io,example.com
EMAIL_DOMAIN_WHITELIST =
+; Comma-separated list of domain names that are not allowed to be used to register on a Gitea instance
+EMAIL_DOMAIN_BLOCKLIST =
; Disallow registration, only allow admins to create accounts.
DISABLE_REGISTRATION = false
; Allow registration only using third-party services, it works only when DISABLE_REGISTRATION is false
diff --git a/docs/content/doc/advanced/config-cheat-sheet.en-us.md b/docs/content/doc/advanced/config-cheat-sheet.en-us.md
index 2c4d01102c..a7f931b047 100644
--- a/docs/content/doc/advanced/config-cheat-sheet.en-us.md
+++ b/docs/content/doc/advanced/config-cheat-sheet.en-us.md
@@ -466,6 +466,7 @@ relation to port exhaustion.
- `DEFAULT_ALLOW_ONLY_CONTRIBUTORS_TO_TRACK_TIME`: **true**: Only allow users with write permissions to track time.
- `EMAIL_DOMAIN_WHITELIST`: **\<empty\>**: If non-empty, list of domain names that can only be used to register
on this instance.
+- `EMAIL_DOMAIN_BLOCKLIST`: **\<empty\>**: If non-empty, list of domain names that cannot be used to register on this instance
- `SHOW_REGISTRATION_BUTTON`: **! DISABLE\_REGISTRATION**: Show Registration Button
- `SHOW_MILESTONES_DASHBOARD_PAGE`: **true** Enable this to show the milestones dashboard page - a view of all the user's milestones
- `AUTO_WATCH_NEW_REPOS`: **true**: Enable this to let all organisation users watch new repos when they are created
diff --git a/docs/content/doc/help/faq.en-us.md b/docs/content/doc/help/faq.en-us.md
index 4346c89c38..b3cf1aa0e8 100644
--- a/docs/content/doc/help/faq.en-us.md
+++ b/docs/content/doc/help/faq.en-us.md
@@ -120,13 +120,14 @@ For more information, refer to Gitea's [API docs]({{< relref "doc/developers/api
There are multiple things you can combine to prevent spammers.
-1. By only whitelisting certain domains with OpenID (see below)
-2. Setting `ENABLE_CAPTCHA` to `true` in your `app.ini` and properly configuring `RECAPTCHA_SECRET` and `RECAPTCHA_SITEKEY`
-3. Settings `DISABLE_REGISTRATION` to `true` and creating new users via the [CLI]({{< relref "doc/usage/command-line.en-us.md" >}}), [API]({{< relref "doc/developers/api-usage.en-us.md" >}}), or Gitea's Admin UI
+1. By whitelisting or blocklisting certain email domains
+2. By only whitelisting certain domains with OpenID (see below)
+3. Setting `ENABLE_CAPTCHA` to `true` in your `app.ini` and properly configuring `RECAPTCHA_SECRET` and `RECAPTCHA_SITEKEY`
+4. Settings `DISABLE_REGISTRATION` to `true` and creating new users via the [CLI]({{< relref "doc/usage/command-line.en-us.md" >}}), [API]({{< relref "doc/developers/api-usage.en-us.md" >}}), or Gitea's Admin UI
-### Only allow certain email domains
+### Only allow/block certain email domains
-You can configure `EMAIL_DOMAIN_WHITELIST` in your app.ini under `[service]`
+You can configure `EMAIL_DOMAIN_WHITELIST` or `EMAIL_DOMAIN_BLOCKLIST` in your app.ini under `[service]`
### Only allow/block certain OpenID providers
diff --git a/modules/forms/user_form.go b/modules/forms/user_form.go
index af36628c30..07733baeba 100644
--- a/modules/forms/user_form.go
+++ b/modules/forms/user_form.go
@@ -95,23 +95,21 @@ func (f *RegisterForm) Validate(req *http.Request, errs binding.Errors) binding.
return middleware.Validate(errs, ctx.Data, f, ctx.Locale)
}
-// IsEmailDomainWhitelisted validates that the email address
-// provided by the user matches what has been configured .
-// If the domain whitelist from the config is empty, it marks the
-// email as whitelisted
-func (f RegisterForm) IsEmailDomainWhitelisted() bool {
- if len(setting.Service.EmailDomainWhitelist) == 0 {
- return true
+// IsEmailDomainListed checks whether the domain of an email address
+// matches a list of domains
+func IsEmailDomainListed(list []string, email string) bool {
+ if len(list) == 0 {
+ return false
}
- n := strings.LastIndex(f.Email, "@")
+ n := strings.LastIndex(email, "@")
if n <= 0 {
return false
}
- domain := strings.ToLower(f.Email[n+1:])
+ domain := strings.ToLower(email[n+1:])
- for _, v := range setting.Service.EmailDomainWhitelist {
+ for _, v := range list {
if strings.ToLower(v) == domain {
return true
}
@@ -120,6 +118,19 @@ func (f RegisterForm) IsEmailDomainWhitelisted() bool {
return false
}
+// IsEmailDomainAllowed validates that the email address
+// provided by the user matches what has been configured .
+// The email is marked as allowed if it matches any of the
+// domains in the whitelist or if it doesn't match any of
+// domains in the blocklist, if any such list is not empty.
+func (f RegisterForm) IsEmailDomainAllowed() bool {
+ if len(setting.Service.EmailDomainWhitelist) == 0 {
+ return !IsEmailDomainListed(setting.Service.EmailDomainBlocklist, f.Email)
+ }
+
+ return IsEmailDomainListed(setting.Service.EmailDomainWhitelist, f.Email)
+}
+
// MustChangePasswordForm form for updating your password after account creation
// by an admin
type MustChangePasswordForm struct {
diff --git a/modules/forms/user_form_test.go b/modules/forms/user_form_test.go
index 6e0518789c..9f67143d12 100644
--- a/modules/forms/user_form_test.go
+++ b/modules/forms/user_form_test.go
@@ -12,17 +12,17 @@ import (
"github.com/stretchr/testify/assert"
)
-func TestRegisterForm_IsDomainWhiteList_Empty(t *testing.T) {
+func TestRegisterForm_IsDomainAllowed_Empty(t *testing.T) {
_ = setting.Service
setting.Service.EmailDomainWhitelist = []string{}
form := RegisterForm{}
- assert.True(t, form.IsEmailDomainWhitelisted())
+ assert.True(t, form.IsEmailDomainAllowed())
}
-func TestRegisterForm_IsDomainWhiteList_InvalidEmail(t *testing.T) {
+func TestRegisterForm_IsDomainAllowed_InvalidEmail(t *testing.T) {
_ = setting.Service
setting.Service.EmailDomainWhitelist = []string{"gitea.io"}
@@ -37,11 +37,11 @@ func TestRegisterForm_IsDomainWhiteList_InvalidEmail(t *testing.T) {
for _, v := range tt {
form := RegisterForm{Email: v.email}
- assert.False(t, form.IsEmailDomainWhitelisted())
+ assert.False(t, form.IsEmailDomainAllowed())
}
}
-func TestRegisterForm_IsDomainWhiteList_ValidEmail(t *testing.T) {
+func TestRegisterForm_IsDomainAllowed_WhitelistedEmail(t *testing.T) {
_ = setting.Service
setting.Service.EmailDomainWhitelist = []string{"gitea.io"}
@@ -59,6 +59,28 @@ func TestRegisterForm_IsDomainWhiteList_ValidEmail(t *testing.T) {
for _, v := range tt {
form := RegisterForm{Email: v.email}
- assert.Equal(t, v.valid, form.IsEmailDomainWhitelisted())
+ assert.Equal(t, v.valid, form.IsEmailDomainAllowed())
+ }
+}
+
+func TestRegisterForm_IsDomainAllowed_BlocklistedEmail(t *testing.T) {
+ _ = setting.Service
+
+ setting.Service.EmailDomainWhitelist = []string{}
+ setting.Service.EmailDomainBlocklist = []string{"gitea.io"}
+
+ tt := []struct {
+ email string
+ valid bool
+ }{
+ {"security@gitea.io", false},
+ {"security@gitea.example", true},
+ {"hdudhdd", true},
+ }
+
+ for _, v := range tt {
+ form := RegisterForm{Email: v.email}
+
+ assert.Equal(t, v.valid, form.IsEmailDomainAllowed())
}
}
diff --git a/modules/setting/service.go b/modules/setting/service.go
index b6611830be..fc4326fde5 100644
--- a/modules/setting/service.go
+++ b/modules/setting/service.go
@@ -20,6 +20,7 @@ var Service struct {
RegisterEmailConfirm bool
RegisterManualConfirm bool
EmailDomainWhitelist []string
+ EmailDomainBlocklist []string
DisableRegistration bool
AllowOnlyExternalRegistration bool
ShowRegistrationButton bool
@@ -72,6 +73,7 @@ func newService() {
Service.RegisterManualConfirm = false
}
Service.EmailDomainWhitelist = sec.Key("EMAIL_DOMAIN_WHITELIST").Strings(",")
+ Service.EmailDomainBlocklist = sec.Key("EMAIL_DOMAIN_BLOCKLIST").Strings(",")
Service.ShowRegistrationButton = sec.Key("SHOW_REGISTRATION_BUTTON").MustBool(!(Service.DisableRegistration || Service.AllowOnlyExternalRegistration))
Service.ShowMilestonesDashboardPage = sec.Key("SHOW_MILESTONES_DASHBOARD_PAGE").MustBool(true)
Service.RequireSignInView = sec.Key("REQUIRE_SIGNIN_VIEW").MustBool()
diff --git a/routers/user/auth.go b/routers/user/auth.go
index bb877767ae..de74055d56 100644
--- a/routers/user/auth.go
+++ b/routers/user/auth.go
@@ -1129,7 +1129,7 @@ func SignUpPost(ctx *context.Context) {
}
}
- if !form.IsEmailDomainWhitelisted() {
+ if !form.IsEmailDomainAllowed() {
ctx.RenderWithErr(ctx.Tr("auth.email_domain_blacklisted"), tplSignUp, &form)
return
}