示例#1
0
class TestLaLetterBuilderCreateLetter:
    QUERY = """
        mutation LaLetterBuilderCreateLetterMutation($input: LaLetterBuilderCreateLetterInput!) {
            output: laLetterBuilderCreateLetter(input: $input) {
                errors { field, messages },
            }
        }
    """

    @pytest.fixture(autouse=True)
    def setup_fixture(self, graphql_client, db):
        self.user = UserFactory(email="*****@*****.**")
        graphql_client.request.user = self.user
        self.graphql_client = graphql_client

    def execute(self, input={}):
        res = self.graphql_client.execute(
            self.QUERY,
            variables={"input": input},
        )
        return res["data"]["output"]

    def test_it_requires_login(self):
        self.graphql_client.request.user = AnonymousUser()
        assert self.execute()["errors"] == one_field_err(
            "You do not have permission to use this form!")

    def test_it_raises_err_when_no_onboarding_info_exists(self):
        assert self.execute()["errors"] == one_field_err(
            "You haven't provided any account details yet!")

    def test_it_raises_err_when_used_on_wrong_site(self):
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "This form can only be used from the LA Letter Builder site.")

    def test_it_creates_letter(
        self,
        settings,
        use_laletterbuilder_site,
    ):
        settings.IS_DEMO_DEPLOYMENT = False
        settings.LANGUAGES = project.locales.ALL.choices
        self.user.locale = "es"
        self.user.save()
        OnboardingInfoFactory(user=self.user)

        assert not HabitabilityLetter.objects.filter(
            user=self.graphql_client.request.user).exists()

        # Create the letter
        assert self.execute()["errors"] == []

        # TODO: add tests for all the other kinds of letters too
        letter = HabitabilityLetter.objects.get(
            user=self.graphql_client.request.user)
        assert letter.locale == "es"
        assert letter.html_content == "<>"
示例#2
0
class AuthenticatedAPITestCase(APITestCase):
    def setUp(self):
        self.user = UserFactory()
        self.user_pass = factory.Faker("password")
        self.user.set_password(self.user_pass)
        self.user.save()

        self.token = Token.objects.create(user=self.user)

        self.client = APIClient()
        self.client.credentials(HTTP_AUTHORIZATION=f"Token {self.token.key}")
示例#3
0
 def create_user(*,
                 email,
                 password,
                 first_name='',
                 last_name='',
                 is_active=True):
     user = UserFactory(email=email,
                        first_name=first_name,
                        last_name=last_name,
                        is_active=is_active)
     user.set_password(password)
     user.save()
     return user
示例#4
0
class TestCommentsViewSet(APITestCase):
    """Tests all CommentsViewSet functionality"""
    def setUp(self) -> None:
        self.user = UserFactory()
        token = Token.objects.get(user=self.user)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        self.topic = TopicFactory(author=self.user)
        self.post = PostFactory(author=self.user, topic=self.topic)
        self.comment1 = CommentFactory(author=self.user, post=self.post)

    def test_get_comments_by_post(self):
        """Get all comments of particular post"""

        CommentFactory(author=self.user, body='Test comment 2', post=self.post)
        data = {
            'post': self.post.id,
        }
        response = self.client.get(reverse('api:comments-list'), data)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(response.data.get('results')), 2)

    def test_delete_comment(self):
        """Test user try to delete comment"""
        response = self.client.delete(
            reverse('api:comments-detail', kwargs={'pk': self.comment1.id}))
        self.assertEqual(response.status_code, status.HTTP_403_FORBIDDEN)
        self.assertTrue(Comment.objects.all().exists())

    def test_successful_comment_deletion(self):
        """Tests that moderators and superusers can delete comments"""

        self.user.is_moderator = True
        self.user.save()
        response = self.client.delete(
            reverse('api:comments-detail', kwargs={'pk': self.comment1.id}))
        self.assertEqual(response.status_code, status.HTTP_204_NO_CONTENT)
        self.assertFalse(Comment.objects.all().exists())

        self.comment1 = CommentFactory(author=self.user, post=self.post)
        self.user.is_moderator = False
        self.user.is_superuser = True
        self.user.save()

        response = self.client.delete(
            reverse('api:comments-detail', kwargs={'pk': self.comment1.id}))
        self.assertEqual(response.status_code, status.HTTP_204_NO_CONTENT)
        self.assertFalse(Comment.objects.all().exists())
示例#5
0
    def test_vendor_number_list_view(self):
        for i in range(3):
            user = UserFactory(is_staff=True)
            user.first_name = 'Test'
            user.save()

            profile = user.profile
            profile.vendor_number = FuzzyText().fuzz()
            profile.save()

        for i in range(3):
            TravelAgentFactory()

        with self.assertNumQueries(2):
            response = self.forced_auth_req('get', reverse('t2f:vendor_numbers'), user=self.unicef_staff)
        response_json = json.loads(response.rendered_content)
        self.assertEqual(len(response_json), 6)
示例#6
0
class TestPostsViewSet(APITestCase):
    """Tests all PostsViewSet functionality"""
    def setUp(self) -> None:
        self.user = UserFactory()
        token = Token.objects.get(user=self.user)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        self.topic = TopicFactory(author=self.user)
        self.post1 = PostFactory(author=self.user, topic=self.topic)
        self.post2 = PostFactory(author=self.user,
                                 topic=self.topic,
                                 body='Test post 2')

    def test_get_posts_by_topic(self):
        """Get all posts of particular topic"""
        data = {'topic': self.topic.id}
        response = self.client.get(reverse('api:posts-list'), data)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(response.data.get('results')), 2)

    def test_patch_post_by_user(self):
        """Tests that user can edit post"""

        data = {'body': 'Edited post body'}
        response = self.client.patch(
            reverse('api:posts-detail', kwargs={'pk': self.post1.id}), data)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(data['body'], response.data.get('body'))

    def test_delete_post_by_user(self):
        """Users cannot delete their """

        response = self.client.delete(
            reverse('api:posts-detail', kwargs={'pk': self.post1.id}))
        self.assertEqual(response.status_code, status.HTTP_403_FORBIDDEN)

    def test_successfult_post_deletion(self):
        """Tests that moderators and admins are able to delete posts"""
        self.user.is_moderator = True
        self.user.save()
        response = self.client.delete(
            reverse('api:posts-detail', kwargs={'pk': self.post1.id}))
        self.assertEqual(response.status_code, status.HTTP_204_NO_CONTENT)
        self.assertEqual(Post.objects.count(), 1)
示例#7
0
class TestAlreadyConfirmedAccount:
    """
    Test AlreadyConfirmedAccount Function.
    """
    def setup(self):
        """
        Sets up test fixtures using Factory Boy instances. See factories.py module
        for more information.
        """
        self.user = UserFactory()
        self.data = {
            'first_name': self.user.first_name,
            'last_name': self.user.last_name,
            'email': self.user.email,
            'password': self.user.password,
            'confirm_password': self.user.password,
            'acct_type': 'IND',
            'toc': True,
        }

    def test_already_confirmed_account_email_response(self, client):
        """
        Test already_confirmed_account email is sent on already verified account.
        """
        self.user.is_active = True
        self.user.save()

        response = client.post('/accounts/reset/', {'email': self.user.email},
                               follow=True)

        assert len(mail.outbox) == 1, 'Returns 1 if email has been sent.'
        assert mail.outbox[
            0].subject == 'Your accounts is already confirmed.', 'Should return email subject line of sent email.'
        assert mail.outbox[0].to == [
            '*****@*****.**'
        ], 'Should return user email used to register.'
        assert 'You have received this email because there was an attempt to reset the activation link for your account.' in str(
            mail.outbox[0].body
        ), 'Returns template text found in the body of sent email.'
示例#8
0
class TestBeginDocusign:
    GRAPHQL = """
    mutation {
        beginDocusign(input: {nextUrl: "/blop"}) {
            errors { field, messages }
            redirectUrl
        }
    }
    """

    @pytest.fixture(autouse=True)
    def setup_fixture(self, db, graphql_client, monkeypatch):
        self.user = UserFactory(email="*****@*****.**", is_email_verified=True)
        graphql_client.request.user = self.user
        self.graphql_client = graphql_client
        self.fake_create_envelope_called = False
        self.fake_create_recipient_view_called = False
        monkeypatch.setattr(hpaction.docusign, "create_envelope_for_hpa",
                            self._fake_create_envelope)
        monkeypatch.setattr(hpaction.docusign, "create_recipient_view_for_hpa",
                            self._fake_create_recipient_view)

    def execute(self):
        return self.graphql_client.execute(
            self.GRAPHQL)["data"]["beginDocusign"]

    def _fake_create_envelope(self, envelope_definition, api_client):
        self.fake_create_envelope_called = True
        return "fake_envelope_id"

    def _fake_create_recipient_view(self, user, envelope_id, api_client,
                                    return_url):
        self.fake_create_recipient_view_called = True
        assert return_url.startswith("https://example.com/docusign/callback?")
        assert user.pk == self.user.pk
        return "https://fake-docusign"

    def ensure_error(self, message):
        assert self.execute()["errors"] == one_field_err(message)

    def test_it_raises_error_on_no_email(self):
        self.user.email = ""
        self.user.save()
        self.ensure_error("You have no email address!")

    def test_it_raises_error_on_unverified_email(self):
        self.user.is_email_verified = False
        self.user.save()
        self.ensure_error("Your email address is not verified!")

    def test_it_raises_error_on_no_docs(self):
        self.ensure_error("You have no HP Action documents to sign!")

    def test_it_works(self, mockdocusign, django_file_storage):
        HPActionDocumentsFactory(user=self.user, kind="EMERGENCY")
        result = self.execute()
        assert result == {"errors": [], "redirectUrl": "https://fake-docusign"}
        assert self.fake_create_envelope_called is True
        assert self.fake_create_recipient_view_called is True
        DocusignEnvelope.objects.get(id="fake_envelope_id")

    def test_it_reuses_existing_envelope(self, mockdocusign,
                                         django_file_storage):
        docs = HPActionDocumentsFactory(user=self.user, kind="EMERGENCY")
        DocusignEnvelopeFactory(docs=docs, id="boop")
        result = self.execute()
        assert result == {"errors": [], "redirectUrl": "https://fake-docusign"}
        assert self.fake_create_envelope_called is False
        assert self.fake_create_recipient_view_called is True
        DocusignEnvelope.objects.get(id="boop")
示例#9
0
class TestUserTeamRequestViewSet(APITestCase):
    def setUp(self) -> None:
        self.user = UserFactory()
        self.user.email_confirmed = True
        self.user.save()
        token = Token.objects.get(user=self.user)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        self.team = TeamFactory(owner=self.user)
        self.another_user1 = AnotherUserFactory()
        self.another_user2 = AnotherUserFactory(username='******',
                                                email='*****@*****.**')
        self.user_team_request = UserTeamRequestFactory(
            user=self.another_user1,
            team=self.team,
        )
        self.user_team_request = UserTeamRequestFactory(
            user=self.another_user2,
            team=self.team,
        )

    def test_get_requests_for_team_by_owner(self):
        """Checks getting all requests for particular team by team owner"""

        params = {'teamID': self.team.id}
        response = self.client.get(
            reverse('api:user-team-requests-get-requests-for-team'), params)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(response.data.get('results')), 2)

    def test_get_request_only_from_one_team(self):
        """Checks that team owner will get only requests from his team"""
        another_user3 = AnotherUserFactory(username='******',
                                           email='*****@*****.**')
        another_user4 = AnotherUserFactory(username='******',
                                           email='*****@*****.**')
        another_user5 = AnotherUserFactory(username='******',
                                           email='*****@*****.**')
        another_user6 = AnotherUserFactory(username='******',
                                           email='*****@*****.**')
        another_team = TeamFactory(
            owner=another_user3,
            name='Soul Eaters',
            description=
            'We`ll destroy all the souls. And the age of darkness will come')
        UserTeamRequestFactory(
            user=another_user4,
            team=another_team,
        )
        UserTeamRequestFactory(
            user=another_user5,
            team=another_team,
        )
        UserTeamRequestFactory(
            user=another_user6,
            team=another_team,
        )
        params = {'teamID': self.team.id}
        response = self.client.get(
            reverse('api:user-team-requests-get-requests-for-team'), params)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(response.data.get('results')), 2)

    def test_get_requests_for_team_by_user(self):
        """Checks that usual user can't fetch requests data"""

        token = Token.objects.get(user=self.another_user1)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        params = {'teamID': self.team.id}
        response = self.client.get(
            reverse('api:user-team-requests-get-requests-for-team'), params)
        self.assertEqual(response.status_code, status.HTTP_403_FORBIDDEN)

    def test_post_request_for_team(self):
        """Tests that user can create requests"""

        usual_user = UserFactory(
            username='******',
            email='*****@*****.**',
        )
        token = Token.objects.get(user=usual_user)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        data = {'team': self.team.id}
        response = self.client.post(reverse('api:user-team-requests-list'),
                                    data=data)
        self.assertEqual(response.status_code, status.HTTP_201_CREATED)
        notification = UserNotification.objects.last()
        notification_message = UserNotification.get_notification_text(
            UserNotification.TEAM_REQUEST_WAS_SENT_WITH_DEACTIVATED_EMAIL,
            username=usual_user.username)
        self.assertEqual(notification.message, notification_message)

    def test_request_created_once(self):
        """Tests that request for user created only once"""

        usual_user = UserFactory(
            username='******',
            email='*****@*****.**',
        )
        token = Token.objects.get(user=usual_user)
        self.client.credentials(HTTP_AUTHORIZATION=f'Token {token.key}')
        data = {'team': self.team.id}
        self.client.post(reverse('api:user-team-requests-list'),
                         data=data)  # first request
        response = self.client.post(reverse('api:user-team-requests-list'),
                                    data=data)  # second request
        self.assertEqual(response.status_code,
                         forum_status.STATUS_222_USER_ALREADY_REQUESTED)

    def test_team_owner_approved_request(self):
        """Tests owner approve user team request flow"""
        data = {
            'approved': True,
        }
        response = self.client.patch(reverse(
            'api:user-team-requests-detail',
            kwargs={'pk': self.user_team_request.id}),
                                     data=data)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(mail.outbox), 1)
        team_request = UserTeamRequest.objects.get(
            id=self.user_team_request.id)
        self.assertTrue(team_request.approved)
        self.assertTrue(team_request.email_was_send)

    def test_team_owner_rejected_request(self):
        """Tests owner reject user team request flow"""
        data = {
            'approved': False,
        }
        response = self.client.patch(reverse(
            'api:user-team-requests-detail',
            kwargs={'pk': self.user_team_request.id}),
                                     data=data)
        self.assertEqual(response.status_code, status.HTTP_200_OK)
        self.assertEqual(len(mail.outbox), 1)
        team_request = UserTeamRequest.objects.get(
            id=self.user_team_request.id)
        self.assertFalse(team_request.approved)
        self.assertTrue(team_request.email_was_send)
示例#10
0
class TestResendActivationLinkView:
    """
    Test of resend_activation_link view.
    """

    def setup(self):
        """
        Sets up test fixtures using Factory Boy instances. See factories.py module
        for more information.
        """
        self.user = UserFactory()

    def test_resend_activation_link_view(self, client):
        """
        Test the resend_activation_link view.
        """

        response = client.get('/accounts/reset/')
        assert response.status_code == 200
        assert response.resolver_match.url_name == 'activation-reset'
        assert response.resolver_match.func.__name__ == 'resend_activation_link'

    def test_resend_activation_view_template_context_html_rendering(self, client):
        """
        Test context and html of resend_activation_link view and template.
        """
        response = client.get('/accounts/reset/')

        assert response.templates[
            0].name == 'users/resend_activation_link.html', 'Should return correct path of view template.'
        assert 'form' in response.context, 'Should return "form" context from view.'
        assert 'Ibhuku | Resend Link' in response.content.decode(
            'utf8'), 'Returns correct page <title> found on page.'

    def test_resend_activation_link_new_email(self, client):
        """
        Test new activation link resent to user.
        """
        response = client.post(
            '/accounts/reset/', {'email': self.user.email}, follow=True)

        assert response.status_code == 200, 'Returns 200 if page redirection is True.'
        assert 'Ibhuku | Activation Link Emailed' in response.content.decode(
            'utf8'), 'Returns correct page <title> found on page.'
        assert response.templates[
            0].name == 'users/account_activation_sent.html', 'Should return rendered template path.'
        assert len(
            mail.outbox) == 1, 'Returns 1 mailbox entry if confirm account email sent.'
        assert mail.outbox[
            0].subject == 'Welcome to Ibhuku.com. Confirm your email.', 'Returns email subject.'
        assert mail.outbox[0].to == ['*****@*****.**']
        assert 'By clicking on the following button/link, you are confirming your email address' in str(mail.outbox[
            0].body), 'Should return email body text.'

    def test_resend_activation_link_new_email_account_confirmed(self, client):
        """
        Test resend activation link response if verified account/email is being used.
        """
        self.user.is_active = True
        self.user.save()

        response = client.post(
            '/accounts/reset/', {'email': self.user.email}, follow=True)

        assert response.resolver_match.url_name == 'activation-exists', 'Returns view url'
        assert 'Ibhuku | Account Exists' in response.content.decode(
            'utf8'), 'Returns correct page <title> found on page.'
        assert response.status_code == 200, 'Returns 200 if successful redirect'
        assert len(
            mail.outbox) == 1, 'Returns 1 mailbox entry if already confirmed email sent.'
        assert mail.outbox[
            0].subject == 'Your accounts is already confirmed.', 'Should return subject of email sent to user.'
        assert mail.outbox[0].to == [
            '*****@*****.**'], 'Should return email message was sent to.'
        assert '*****@*****.**' in str(mail.outbox[
            0].body), 'Should return the user email address used to confirm the account in email text body.'
示例#11
0
class TestUserModel:
    """
    Test for the Users Model.
    """

    def setup(self):
        """
        Sets up test fixtures using Factory Boy instances. See factories.py module
        for more information.
        """
        self.user1 = UserFactory()
        self.user2 = UserFactory(
            first_name='John', last_name='Doe', email='*****@*****.**')
        self.users = User.objects.all()

    # Test of User Model created instances
    def test_user1_instance_created(self):
        """
        Test for creation of a user instance in the database.
        """
        assert self.user1.first_name == 'Testy0', 'Should return user first name.'
        assert self.user1.email == '*****@*****.**', 'Should return user email.'
        assert self.user1.password == 'testpassword0000', 'Should return user password.'

    def test_multiple_users_saved_in_database(self):
        """
        Test for number of user instances created in database.
        """
        assert len(
            self.users) == 2, 'Should return number of instances created in database'

    def test_user_instance_get_full_name_method(self):
        """
        Test the user model's get_full_name() method.
        """
        assert self.user1.get_full_name(
        ) == 'Testy4McTesty4', 'Should return full_name method value.'
        assert self.user2.get_full_name(
        ) == 'JohnDoe', 'Should return full_name method value.'

    def test_user_get_short_name_method(self):
        """
        Test the user model's get_short_name() method.
        """
        assert self.user1.get_short_name(
        ) == 'TMcTesty6', 'Should return short_name method value.'
        assert self.user2.get_short_name(
        ) == 'JDoe', 'Should return short_name method value.'

    def test_user_model_saves(self):
        """
        Test user model saves/updates user changed/new data.
        """
        self.user1.password = '******'
        self.user1.is_active = True
        self.user1.acct_type = 'EDU'
        self.user1.save()
        assert self.user1.password == 'testpassword12345'
        assert self.user1.is_active == True
        assert self.user1.acct_type == 'EDU'

    # Test of User Model methods
    def test_user_model_unicode_method(self):
        """
        Test the user model's __unicode__() method.
        """
        assert self.user1.__unicode__(
        ) == 'Testy10McTesty10', 'Should return unicode method value.'
        assert self.user2.__unicode__(
        ) == 'JohnDoe', 'Should return unicode method value.'

    def test_user_model_str_method(self):
        """
        Test the user model's __str__() method.
        """
        assert self.user1.__str__(
        ) == 'Testy12McTesty12', 'Should return str method value.'
        assert self.user2.__str__(
        ) == 'JohnDoe', 'Should return str method value.'
示例#12
0
class TestCoreLogic(APITestCase):
    def setUp(self) -> None:
        self.user = UserFactory()

    def test_coins_purchase_functionality(self):
        """Checks that coins calculates properly"""

        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_500_COINS)
        self.assertEqual(self.user.coins, constants.COINS_500)
        self.user.coins = 0
        self.user.save()
        notification_message = UserNotification.get_notification_text(
            UserNotification.SUCCESSFUL_COINS_PURCHASE,
            username=self.user.username,
            amount=constants.COINS_500)
        notification = UserNotification.objects.last()
        self.assertEqual(notification.message, notification_message)
        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_750_COINS)
        self.assertEqual(self.user.coins, constants.COINS_750)
        self.user.coins = 0
        self.user.save()
        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_1000_COINS)
        self.assertEqual(self.user.coins, constants.COINS_1000)
        self.user.coins = 0
        self.user.save()
        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_2000_COINS)
        self.assertEqual(self.user.coins, constants.COINS_2000)
        self.user.coins = 0
        self.user.save()
        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_5000_COINS)
        self.assertEqual(self.user.coins, constants.COINS_5000)
        self.user.coins = 0
        self.user.save()
        calculate_coins_for_user(user=self.user,
                                 amount=constants.CENTS_FOR_10000_COINS)
        self.assertEqual(self.user.coins, constants.COINS_10000)
        self.user.coins = 0
        self.user.save()

    def test_delete_moderators_removed_topics(self):
        two_weeks_ago = datetime.now() - timedelta(days=14)
        for index in range(5):
            TopicFactory(removed_by_moderator=True, removed_at=two_weeks_ago)
        delete_moderators_removed_topics()
        existing_topics = Topic.objects.all()
        self.assertFalse(bool(existing_topics))
示例#13
0
class TestLaLetterBuilderSendLetter:
    SEND_QUERY = """
    mutation laLetterBuilderSendLetter($input: LaLetterBuilderSendLetterInput!) {
        output: laLetterBuilderSendLetter(input: $input) {
            errors { field, messages },
        }
    }
    """

    @pytest.fixture(autouse=True)
    def setup_fixture(self, graphql_client, db):
        self.user = UserFactory(email="*****@*****.**")
        graphql_client.request.user = self.user
        self.graphql_client = graphql_client

    def create_landlord_details(self):
        LandlordDetailsFactory(user=self.user,
                               email="*****@*****.**")

    def execute(self, input={}):
        res = self.graphql_client.execute(
            self.SEND_QUERY,
            variables={"input": input},
        )
        return res["data"]["output"]

    def test_it_requires_login(self):
        self.graphql_client.request.user = AnonymousUser()
        assert self.execute()["errors"] == one_field_err(
            "You do not have permission to use this form!")

    def test_it_raises_err_when_no_onboarding_info_exists(self):
        assert self.execute()["errors"] == one_field_err(
            "You haven't provided any account details yet!")

    def test_it_raises_err_when_no_landlord_details_exist(self):
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "You haven't provided any landlord details yet!")

    def test_it_raises_err_when_used_on_wrong_site(self):
        self.create_landlord_details()
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "This form can only be used from the LA Letter Builder site.")

    def test_it_sends_letter(
        self,
        settings,
        allow_lambda_http,
        use_laletterbuilder_site,
        requests_mock,
        mailoutbox,
        smsoutbox,
        mocklob,
    ):
        user = self.graphql_client.request.user
        settings.IS_DEMO_DEPLOYMENT = False
        settings.LANGUAGES = project.locales.ALL.choices
        self.user.locale = "es"
        self.user.save()
        self.create_landlord_details()
        OnboardingInfoFactory(user=self.user)
        letter_obj = HabitabilityLetter(user=user,
                                        locale="es",
                                        html_content="<test/>")
        letter_obj.save()

        blank_letter = HabitabilityLetter.objects.get(user=user,
                                                      letter_sent_at=None,
                                                      letter_emailed_at=None)
        assert blank_letter.html_content == "<test/>"

        # Send the letter
        assert self.execute()["errors"] == []

        sent_letter = HabitabilityLetter.objects.get(
            user=self.graphql_client.request.user)
        assert ("LETTER TEXT" in sent_letter.html_content
                )  # TODO: change this when we get real text in there
        assert "Boop Jones" in sent_letter.html_content
        assert 'lang="en"' in sent_letter.html_content
        assert 'lang="es"' in sent_letter.localized_html_content
示例#14
0
class TestNorentSendLetterV2:
    QUERY = """
    mutation {
        norentSendLetterV2(input: {}) {
            errors { field, messages }
        }
    }
    """

    @pytest.fixture(autouse=True)
    def setup_fixture(self, graphql_client, db):
        self.user = UserFactory(email="*****@*****.**")
        graphql_client.request.user = self.user
        self.graphql_client = graphql_client

    def create_landlord_details(self):
        LandlordDetailsFactory(user=self.user,
                               email="*****@*****.**")

    def execute(self):
        res = self.graphql_client.execute(self.QUERY)
        return res["data"]["norentSendLetterV2"]

    def test_it_requires_login(self):
        self.graphql_client.request.user = AnonymousUser()
        assert self.execute()["errors"] == one_field_err(
            "You do not have permission to use this form!")

    def test_it_raises_err_when_no_rent_periods_are_chosen(self):
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "You have not chosen any rent periods!")

    def test_it_raises_err_when_letter_already_sent(self):
        letter = LetterFactory(user=self.user)
        UpcomingLetterRentPeriodFactory(
            user=self.user, rent_period=letter.rent_periods.all()[0])
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "You have already sent a letter for one of the rent periods!")

    def test_it_raises_err_when_no_onboarding_info_exists(self):
        UpcomingLetterRentPeriodFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "You haven't provided any account details yet!")

    def test_it_raises_err_when_no_landlord_details_exist(self):
        UpcomingLetterRentPeriodFactory(user=self.user)
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "You haven't provided any landlord details yet!")

    def test_it_raises_err_when_used_on_wrong_site(self):
        UpcomingLetterRentPeriodFactory(user=self.user)
        self.create_landlord_details()
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == one_field_err(
            "This form can only be used from the NoRent site.")

    def test_it_works(
        self,
        allow_lambda_http,
        use_norent_site,
        requests_mock,
        mailoutbox,
        smsoutbox,
        settings,
        mocklob,
    ):
        settings.IS_DEMO_DEPLOYMENT = False
        settings.LANGUAGES = project.locales.ALL.choices
        UpcomingLetterRentPeriodFactory(user=self.user)
        self.user.locale = "es"
        self.user.save()
        self.create_landlord_details()
        OnboardingInfoFactory(user=self.user)
        assert self.execute()["errors"] == []

        assert UpcomingLetterRentPeriod.objects.get_for_user(self.user) == []
        letter = Letter.objects.get(user=self.graphql_client.request.user)
        assert len(letter.rent_periods.all()) == 1
        assert str(letter.latest_rent_period.payment_date) == "2020-05-01"
        assert letter.locale == "es"
        assert "unable to pay rent" in letter.html_content
        assert "Boop Jones" in letter.html_content
        assert 'lang="en"' in letter.html_content
        assert 'lang="es"' in letter.localized_html_content
        assert letter.letter_sent_at is not None
        assert letter.tracking_number == mocklob.sample_letter[
            "tracking_number"]
        assert letter.fully_processed_at is not None

        assert len(mailoutbox) == 2
        ll_mail = mailoutbox[0]
        assert ll_mail.to == ["*****@*****.**"]
        assert "letter attached" in ll_mail.body
        assert "Boop Jones" in ll_mail.body
        assert "sent on behalf" in ll_mail.subject
        assert len(ll_mail.attachments) == 1
        assert letter.letter_emailed_at is not None

        user_mail = mailoutbox[1]
        assert user_mail.to == ["*****@*****.**"]
        assert "https://example.com/es/faqs" in user_mail.body
        assert "Hola Boop" in user_mail.body
        assert "Tu carta de NoRent y pasos siguientes importantes" in user_mail.subject

        assert len(smsoutbox) == 1
        assert "Boop Jones" in smsoutbox[0].body
        assert "USPS" in smsoutbox[0].body

        assert len(user_mail.attachments) == 1