mirror of
https://blitiri.com.ar/repos/chasquid
synced 2025-12-19 14:57:04 +00:00
userdb: Add support for receive-only users
Some use cases, like receive-only MTAs, need domain users for receiving emails, but have no real need for passwords since they will never use submission. Today, that is not supported, and those use-cases require the administrator to come up with a password unnecessarily, adding complexity and possibly risk. This patch implements "receive-only users", which don't have a valid password, thus exist for the purposes of delivering mail, but always fail authentication. See https://github.com/albertito/chasquid/issues/44 for more details and rationale. Thanks to xavierg who suggested this feature on IRC.
This commit is contained in:
@@ -122,24 +122,27 @@ func TestWrite(t *testing.T) {
|
||||
t.Fatalf("expected %v, got %v", emptyDB, db)
|
||||
}
|
||||
|
||||
// Add two users, write, and load again.
|
||||
// Add users, write, and load again.
|
||||
if err := db.AddUser("user1", "passwd1"); err != nil {
|
||||
t.Fatalf("failed to add user1: %v", err)
|
||||
}
|
||||
if err := db.AddUser("ñoño", "añicos"); err != nil {
|
||||
t.Fatalf("failed to add ñoño: %v", err)
|
||||
}
|
||||
if err := db.AddDeniedUser("ñaca"); err != nil {
|
||||
t.Fatalf("failed to add ñaca: %v", err)
|
||||
}
|
||||
if err := db.Write(); err != nil {
|
||||
t.Fatalf("error writing database: %v", err)
|
||||
}
|
||||
|
||||
db = mustLoad(t, fname)
|
||||
for _, name := range []string{"user1", "ñoño"} {
|
||||
for _, name := range []string{"user1", "ñoño", "ñaca"} {
|
||||
if !db.Exists(name) {
|
||||
t.Errorf("user %q not in database", name)
|
||||
}
|
||||
if db.db.Users[name].GetScheme() == nil {
|
||||
t.Errorf("user %q not using scrypt: %#v", name, db.db.Users[name])
|
||||
t.Errorf("user %q missing scheme: %#v", name, db.db.Users[name])
|
||||
}
|
||||
}
|
||||
|
||||
@@ -153,6 +156,8 @@ func TestWrite(t *testing.T) {
|
||||
{"user1", "passwd12", false},
|
||||
{"ñoño", "añicos", true},
|
||||
{"ñoño", "anicos", false},
|
||||
{"ñaca", "", false},
|
||||
{"ñaca", "lalala", false},
|
||||
{"notindb", "something", false},
|
||||
{"", "", false},
|
||||
{" ", " ", false},
|
||||
@@ -202,6 +207,11 @@ func TestInvalidUsername(t *testing.T) {
|
||||
if err == nil {
|
||||
t.Errorf("AddUser(%q) worked, expected it to fail", name)
|
||||
}
|
||||
|
||||
err = db.AddDeniedUser(name)
|
||||
if err == nil {
|
||||
t.Errorf("AddDeniedUser(%q) worked, expected it to fail", name)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -235,6 +245,24 @@ func TestPlainScheme(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
// Test the denied scheme.
|
||||
func TestDeniedScheme(t *testing.T) {
|
||||
fname := mustCreateDB(t, "")
|
||||
defer removeIfSuccessful(t, fname)
|
||||
db := mustLoad(t, fname)
|
||||
|
||||
db.db.Users["user"] = &Password{Scheme: &Password_Denied{}}
|
||||
err := db.Write()
|
||||
if err != nil {
|
||||
t.Errorf("Write failed: %v", err)
|
||||
}
|
||||
|
||||
db = mustLoad(t, fname)
|
||||
if db.Authenticate("user", "anything") {
|
||||
t.Errorf("denied authentication worked but it shouldn't")
|
||||
}
|
||||
}
|
||||
|
||||
func TestReload(t *testing.T) {
|
||||
content := "users:< key: 'u1' value:< plain:< password: 'pass' >>>"
|
||||
fname := mustCreateDB(t, content)
|
||||
@@ -326,4 +354,12 @@ func TestExists(t *testing.T) {
|
||||
if !db.Exists("user") {
|
||||
t.Errorf("known user does not exist")
|
||||
}
|
||||
|
||||
if err := db.AddDeniedUser("denieduser"); err != nil {
|
||||
t.Fatalf("error adding user: %v", err)
|
||||
}
|
||||
|
||||
if !db.Exists("denieduser") {
|
||||
t.Errorf("known (denied) user does not exist")
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user