From 30970749e30d89111bc58f4ef80c76ef88c70397 Mon Sep 17 00:00:00 2001 From: Emelia Smith Date: Wed, 7 Aug 2024 20:25:08 +0200 Subject: [PATCH] fix: Send create user email for password resets where we have an email and person, but no user. (#7729) * fix: Send create user email for password resets where we have an email and person, but no user account This fixes https://github.com/ietf-tools/datatracker/issues/6458 * fix: create User straight away and use nomral password reset --------- Co-authored-by: Robert Sparks --- ietf/ietfauth/tests.py | 18 ++++++++++++++++++ ietf/ietfauth/views.py | 16 +++++++++++++--- 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/ietf/ietfauth/tests.py b/ietf/ietfauth/tests.py index 6a85c6eb1..722c1e8b6 100644 --- a/ietf/ietfauth/tests.py +++ b/ietf/ietfauth/tests.py @@ -527,6 +527,24 @@ class IetfAuthTests(TestCase): self.assertIn(secondary_address, to) self.assertNotIn(inactive_secondary_address, to) + def test_reset_password_without_user(self): + """Reset password using email address for person without a user account""" + url = urlreverse('ietf.ietfauth.views.password_reset') + email = EmailFactory() + person = email.person + # Remove the user object from the person to get a Email/Person without User: + person.user = None + person.save() + # Remove the remaining User record, since reset_password looks for that by username: + User.objects.filter(username__iexact=email.address).delete() + empty_outbox() + r = self.client.post(url, { 'username': email.address }) + self.assertEqual(len(outbox), 1) + lastReceivedEmail = outbox[-1] + self.assertIn(email.address, lastReceivedEmail.get('To')) + self.assertTrue(lastReceivedEmail.get('Subject').startswith("Confirm password reset")) + self.assertContains(r, "Your password reset request has been successfully received", status_code=200) + def test_review_overview(self): review_req = ReviewRequestFactory() assignment = ReviewAssignmentFactory(review_request=review_req,reviewer=EmailFactory(person__user__username='reviewer')) diff --git a/ietf/ietfauth/views.py b/ietf/ietfauth/views.py index 61c7b929b..32bb5c92b 100644 --- a/ietf/ietfauth/views.py +++ b/ietf/ietfauth/views.py @@ -491,9 +491,19 @@ def password_reset(request): if not user: # try to find user ID from the email address email = Email.objects.filter(address=submitted_username).first() - if email and email.person and email.person.user: - user = email.person.user - + if email and email.person: + if email.person.user: + user = email.person.user + else: + # Create a User record with this (conditioned by way of Email) username + # Don't bother setting the name or email fields on User - rely on the + # Person pointer. + user = User.objects.create( + username=email.address.lower(), + is_active=True, + ) + email.person.user = user + email.person.save() if user and user.person.email_set.filter(active=True).exists(): data = { 'username': user.username,