Support wildcard in email domain allow/block list (#24831)

Replace #20257 (which is stale and incomplete)

Close #20255

Major changes:

* Deprecate the "WHITELIST", use "ALLOWLIST"
* Add wildcard support for EMAIL_DOMAIN_ALLOWLIST/EMAIL_DOMAIN_BLOCKLIST
* Update example config file and document
* Improve tests
This commit is contained in:
wxiaoguang 2023-05-22 08:05:44 +08:00 committed by GitHub
parent 19993d8814
commit 2cb66fff60
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 118 additions and 34 deletions

View file

@ -16,6 +16,7 @@ import (
"code.gitea.io/gitea/modules/web/middleware"
"gitea.com/go-chi/binding"
"github.com/gobwas/glob"
)
// InstallForm form for installation page
@ -105,8 +106,8 @@ func (f *RegisterForm) Validate(req *http.Request, errs binding.Errors) binding.
// 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 {
func IsEmailDomainListed(globs []glob.Glob, email string) bool {
if len(globs) == 0 {
return false
}
@ -117,8 +118,8 @@ func IsEmailDomainListed(list []string, email string) bool {
domain := strings.ToLower(email[n+1:])
for _, v := range list {
if strings.ToLower(v) == domain {
for _, g := range globs {
if g.Match(domain) {
return true
}
}
@ -131,12 +132,12 @@ func IsEmailDomainListed(list []string, email string) bool {
// 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)
func (f *RegisterForm) IsEmailDomainAllowed() bool {
if len(setting.Service.EmailDomainAllowList) == 0 {
return !IsEmailDomainListed(setting.Service.EmailDomainBlockList, f.Email)
}
return IsEmailDomainListed(setting.Service.EmailDomainWhitelist, f.Email)
return IsEmailDomainListed(setting.Service.EmailDomainAllowList, f.Email)
}
// MustChangePasswordForm form for updating your password after account creation

View file

@ -10,13 +10,17 @@ import (
auth_model "code.gitea.io/gitea/models/auth"
"code.gitea.io/gitea/modules/setting"
"github.com/gobwas/glob"
"github.com/stretchr/testify/assert"
)
func TestRegisterForm_IsDomainAllowed_Empty(t *testing.T) {
_ = setting.Service
oldService := setting.Service
defer func() {
setting.Service = oldService
}()
setting.Service.EmailDomainWhitelist = []string{}
setting.Service.EmailDomainAllowList = nil
form := RegisterForm{}
@ -24,15 +28,18 @@ func TestRegisterForm_IsDomainAllowed_Empty(t *testing.T) {
}
func TestRegisterForm_IsDomainAllowed_InvalidEmail(t *testing.T) {
_ = setting.Service
oldService := setting.Service
defer func() {
setting.Service = oldService
}()
setting.Service.EmailDomainWhitelist = []string{"gitea.io"}
setting.Service.EmailDomainAllowList = []glob.Glob{glob.MustCompile("gitea.io")}
tt := []struct {
email string
}{
{"securitygieqqq"},
{"hdudhdd"},
{"invalid-email"},
{"gitea.io"},
}
for _, v := range tt {
@ -42,10 +49,13 @@ func TestRegisterForm_IsDomainAllowed_InvalidEmail(t *testing.T) {
}
}
func TestRegisterForm_IsDomainAllowed_WhitelistedEmail(t *testing.T) {
_ = setting.Service
func TestRegisterForm_IsDomainAllowed_AllowedEmail(t *testing.T) {
oldService := setting.Service
defer func() {
setting.Service = oldService
}()
setting.Service.EmailDomainWhitelist = []string{"gitea.io"}
setting.Service.EmailDomainAllowList = []glob.Glob{glob.MustCompile("gitea.io"), glob.MustCompile("*.allow")}
tt := []struct {
email string
@ -53,8 +63,11 @@ func TestRegisterForm_IsDomainAllowed_WhitelistedEmail(t *testing.T) {
}{
{"security@gitea.io", true},
{"security@gITea.io", true},
{"hdudhdd", false},
{"invalid", false},
{"seee@example.com", false},
{"user@my.allow", true},
{"user@my.allow1", false},
}
for _, v := range tt {
@ -64,11 +77,14 @@ func TestRegisterForm_IsDomainAllowed_WhitelistedEmail(t *testing.T) {
}
}
func TestRegisterForm_IsDomainAllowed_BlocklistedEmail(t *testing.T) {
_ = setting.Service
func TestRegisterForm_IsDomainAllowed_BlockedEmail(t *testing.T) {
oldService := setting.Service
defer func() {
setting.Service = oldService
}()
setting.Service.EmailDomainWhitelist = []string{}
setting.Service.EmailDomainBlocklist = []string{"gitea.io"}
setting.Service.EmailDomainAllowList = nil
setting.Service.EmailDomainBlockList = []glob.Glob{glob.MustCompile("gitea.io"), glob.MustCompile("*.block")}
tt := []struct {
email string
@ -76,7 +92,10 @@ func TestRegisterForm_IsDomainAllowed_BlocklistedEmail(t *testing.T) {
}{
{"security@gitea.io", false},
{"security@gitea.example", true},
{"hdudhdd", true},
{"invalid", true},
{"user@my.block", false},
{"user@my.block1", true},
}
for _, v := range tt {