From 4680d504de03cf30e593f3454e489628d134a735 Mon Sep 17 00:00:00 2001 From: arunikaydav42 Date: Sat, 15 Feb 2020 11:36:48 +0530 Subject: [PATCH] invite: Fix invitations removed from list too soon. On invitations panel, invites were being removed when the user clicked on invitation's link. Now we only remove it when the user completes registration. Fixes: #12281 --- confirmation/models.py | 5 +++-- zerver/lib/actions.py | 2 ++ zerver/lib/test_classes.py | 6 +++--- zerver/tests/test_signup.py | 37 +++++++++++++++++++++++++++++++++--- zerver/views/registration.py | 3 +-- 5 files changed, 43 insertions(+), 10 deletions(-) diff --git a/confirmation/models.py b/confirmation/models.py index ba2587a988..c958e57584 100644 --- a/confirmation/models.py +++ b/confirmation/models.py @@ -43,7 +43,8 @@ def generate_key() -> str: ConfirmationObjT = Union[MultiuseInvite, PreregistrationUser, EmailChangeStatus] def get_object_from_key(confirmation_key: str, - confirmation_type: int) -> ConfirmationObjT: + confirmation_type: int, + activate_object: bool=True) -> ConfirmationObjT: # Confirmation keys used to be 40 characters if len(confirmation_key) not in (24, 40): raise ConfirmationKeyException(ConfirmationKeyException.WRONG_LENGTH) @@ -58,7 +59,7 @@ def get_object_from_key(confirmation_key: str, raise ConfirmationKeyException(ConfirmationKeyException.EXPIRED) obj = confirmation.content_object - if hasattr(obj, "status"): + if activate_object and hasattr(obj, "status"): obj.status = getattr(settings, 'STATUS_ACTIVE', 1) obj.save(update_fields=['status']) return obj diff --git a/zerver/lib/actions.py b/zerver/lib/actions.py index 4edeaac2fe..2e86a74ede 100644 --- a/zerver/lib/actions.py +++ b/zerver/lib/actions.py @@ -362,6 +362,8 @@ def process_new_human_user(user_profile: UserProfile, realm_creation: bool=False) -> None: mit_beta_user = user_profile.realm.is_zephyr_mirror_realm if prereg_user is not None: + prereg_user.status = confirmation_settings.STATUS_ACTIVE + prereg_user.save(update_fields=['status']) streams = prereg_user.streams.all() acting_user: Optional[UserProfile] = prereg_user.referred_by else: diff --git a/zerver/lib/test_classes.py b/zerver/lib/test_classes.py index d741e15152..fae16ad36a 100644 --- a/zerver/lib/test_classes.py +++ b/zerver/lib/test_classes.py @@ -418,7 +418,8 @@ class ZulipTestCase(TestCase): from_confirmation: Optional[str]='', full_name: Optional[str]=None, timezone: Optional[str]='', realm_in_root_domain: Optional[str]=None, default_stream_groups: Optional[List[str]]=[], - source_realm: Optional[str]='', **kwargs: Any) -> HttpResponse: + source_realm: Optional[str]='', + key: Optional[str]=None, **kwargs: Any) -> HttpResponse: """ Stage two of the two-step registration process. @@ -429,13 +430,12 @@ class ZulipTestCase(TestCase): """ if full_name is None: full_name = email.replace("@", "_") - payload = { 'full_name': full_name, 'password': password, 'realm_name': realm_name, 'realm_subdomain': realm_subdomain, - 'key': find_key_by_email(email), + 'key': key if key is not None else find_key_by_email(email), 'timezone': timezone, 'terms': True, 'from_confirmation': from_confirmation, diff --git a/zerver/tests/test_signup.py b/zerver/tests/test_signup.py index b6a4c90116..5335f76213 100644 --- a/zerver/tests/test_signup.py +++ b/zerver/tests/test_signup.py @@ -33,6 +33,7 @@ from zerver.models import ( CustomProfileFieldValue, DefaultStream, PreregistrationUser, Realm, Recipient, Message, ScheduledEmail, UserProfile, UserMessage, Stream, Subscription, flush_per_request_caches, get_system_bot, + get_user_by_delivery_email ) from zerver.lib.actions import ( do_change_user_role, @@ -40,8 +41,7 @@ from zerver.lib.actions import ( do_create_default_stream_group, do_add_default_stream, do_create_realm, - get_default_streams_for_realm, -) + get_default_streams_for_realm) from zerver.lib.send_email import send_future_email, FromAddress, \ deliver_email from zerver.lib.initial_password import initial_password @@ -604,7 +604,7 @@ class LoginTest(ZulipTestCase): with queries_captured() as queries: self.register(self.nonreg_email('test'), "test") # Ensure the number of queries we make is not O(streams) - self.assertEqual(len(queries), 77) + self.assertEqual(len(queries), 78) user_profile = self.nonreg_user('test') self.assert_logged_in_user_id(user_profile.id) self.assertFalse(user_profile.enable_stream_desktop_notifications) @@ -1749,6 +1749,37 @@ class InvitationsTestCase(InviteUserBase): error_result = self.client_delete('/json/invites/' + str(prereg_user.id)) self.assert_json_error(error_result, "No such invitation") + def test_prereg_user_status(self) -> None: + email = self.nonreg_email("alice") + password = "password" + realm = get_realm('zulip') + + inviter = UserProfile.objects.first() + prereg_user = PreregistrationUser.objects.create( + email=email, referred_by=inviter, realm=realm) + + confirmation_link = create_confirmation_link(prereg_user, 'host', Confirmation.USER_REGISTRATION) + registration_key = confirmation_link.split('/')[-1] + + result = self.client_post( + "/accounts/register/", + {"key": registration_key, + "from_confirmation": "1", + "full_name": "alice"}) + self.assertEqual(result.status_code, 200) + confirmation = Confirmation.objects.get(confirmation_key=registration_key) + prereg_user = confirmation.content_object + self.assertEqual(prereg_user.status, 0) + + result = self.submit_reg_form_for_user(email, password, key=registration_key) + self.assertEqual(result.status_code, 302) + prereg_user = PreregistrationUser.objects.get( + email=email, referred_by=inviter, realm=realm) + self.assertEqual(prereg_user.status, confirmation_settings.STATUS_ACTIVE) + user = get_user_by_delivery_email(email, realm) + self.assertIsNotNone(user) + self.assertEqual(user.delivery_email, email) + class InviteeEmailsParserTests(TestCase): def setUp(self) -> None: super().setUp() diff --git a/zerver/views/registration.py b/zerver/views/registration.py index badf7c6aef..90bcf70815 100644 --- a/zerver/views/registration.py +++ b/zerver/views/registration.py @@ -56,7 +56,7 @@ def check_prereg_key_and_redirect(request: HttpRequest, confirmation_key: str) - return render_confirmation_key_error( request, ConfirmationKeyException(ConfirmationKeyException.DOES_NOT_EXIST)) try: - get_object_from_key(confirmation_key, confirmation.type) + get_object_from_key(confirmation_key, confirmation.type, activate_object=False) except ConfirmationKeyException as exception: return render_confirmation_key_error(request, exception) @@ -92,7 +92,6 @@ def accounts_register(request: HttpRequest) -> HttpResponse: return render_confirmation_key_error( request, ConfirmationKeyException(ConfirmationKeyException.DOES_NOT_EXIST)) realm = prereg_user.realm - try: email_allowed_for_realm(email, realm) except DomainNotAllowedForRealmError: