Skip to content

Commit afc0998

Browse files
committed
fixup! [#2816] Split user/password auth from token verification
1 parent e1899ae commit afc0998

File tree

2 files changed

+37
-34
lines changed

2 files changed

+37
-34
lines changed

src/open_inwoner/accounts/backends.py

+35-32
Original file line numberDiff line numberDiff line change
@@ -27,29 +27,31 @@ class UserModelEmailBackend(ModelBackend):
2727
"""
2828

2929
def authenticate(self, request, username=None, password=None):
30+
if not username or not password:
31+
return
32+
3033
User = get_user_model()
31-
if username and password:
32-
try:
33-
user = User.objects.get(
34-
email__iexact=username,
35-
login_type=LoginTypeChoices.default,
36-
)
37-
if check_password(
38-
password, user.password
39-
) and self.user_can_authenticate(user):
40-
return user
41-
except User.MultipleObjectsReturned:
42-
# Found multiple users with this email (shouldn't happen if we added checks)
43-
# Run the default password hasher once to reduce the timing
44-
# difference between an existing and a nonexistent user (#20760).
45-
User().set_password(password)
46-
return None
47-
except User.DoesNotExist:
48-
# No user was found, return None - triggers default login failed
49-
# Run the default password hasher once to reduce the timing
50-
# difference between an existing and a nonexistent user (#20760).
51-
User().set_password(password)
52-
return None
34+
try:
35+
user = User.objects.get(
36+
email__iexact=username,
37+
login_type=LoginTypeChoices.default,
38+
)
39+
if check_password(password, user.password) and self.user_can_authenticate(
40+
user
41+
):
42+
return user
43+
except User.MultipleObjectsReturned:
44+
# Found multiple users with this email (shouldn't happen if we added checks)
45+
# Run the default password hasher once to reduce the timing
46+
# difference between an existing and a nonexistent user (#20760).
47+
User().set_password(password)
48+
return None
49+
except User.DoesNotExist:
50+
# No user was found, return None - triggers default login failed
51+
# Run the default password hasher once to reduce the timing
52+
# difference between an existing and a nonexistent user (#20760).
53+
User().set_password(password)
54+
return None
5355

5456

5557
class Verify2FATokenBackend(BaseBackend):
@@ -58,17 +60,18 @@ class Verify2FATokenBackend(BaseBackend):
5860
"""
5961

6062
def authenticate(self, request, *, user=None, token=None):
61-
# 2FA with sms verification
62-
if user and token:
63-
accepted, drift = accept_totp(
64-
key=user.seed,
65-
response=token,
66-
period=getattr(settings, "ACCOUNTS_USER_TOKEN_EXPIRE_TIME", 300),
67-
)
68-
if not accepted:
69-
return None
63+
if not user or not token:
64+
return
7065

71-
return user
66+
accepted, drift = accept_totp(
67+
key=user.seed,
68+
response=token,
69+
period=getattr(settings, "ACCOUNTS_USER_TOKEN_EXPIRE_TIME", 300),
70+
)
71+
if not accepted:
72+
return None
73+
74+
return user
7275

7376

7477
class CustomAxesBackend(AxesBackend):

src/open_inwoner/accounts/tests/test_backends.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,7 @@ class UserModelEmailBackendTestCase(TestCase):
8787
def setUpTestData(cls):
8888
super().setUpTestData()
8989

90-
cls.password = "keepitsecert"
90+
cls.password = "keepitsecret"
9191
cls.user = UserFactory(
9292
login_type=LoginTypeChoices.default, password=cls.password
9393
)
@@ -142,6 +142,7 @@ def test_missing_username_and_or_password_returns_none(self):
142142
"open_inwoner.accounts.backends.Verify2FATokenBackend",
143143
]
144144
)
145+
@freeze_time("2023-05-22 12:05:01")
145146
class Verify2FATokenBackendTestCase(TestCase):
146147
@classmethod
147148
def setUpTestData(cls):
@@ -151,7 +152,6 @@ def setUpTestData(cls):
151152
cls.expires_in = getattr(settings, "ACCOUNTS_USER_TOKEN_EXPIRE_TIME", 300)
152153
cls.make_token = lambda: totp(cls.user.seed, period=cls.expires_in)
153154

154-
@freeze_time("2023-05-22 12:05:01")
155155
def test_valid_token_and_user_returns_user(self):
156156
request = RequestFactory().get(reverse("verify_token"))
157157

0 commit comments

Comments
 (0)