def setUp(self): super(CertificateStatsTestCase, self).setUp() # if we generate only one document for each, we won't know if we used a value in the wrong case GeneratedCertificateFactory(course_id=self.course.id, user=UserFactory(), status=CertificateStatuses.notpassing) for _ in range(2): GeneratedCertificateFactory( course_id=self.course.id, user=UserFactory(), status=CertificateStatuses.downloadable) for _ in range(3): GeneratedCertificateFactory(course_id=self.course.id, user=UserFactory(), status=CertificateStatuses.notpassing, mode="verified") for _ in range(4): GeneratedCertificateFactory( course_id=self.course.id, user=UserFactory(), status=CertificateStatuses.downloadable, mode="verified") self.response = self.get_response("course-dashboard:certificate-stats", self.course)
def test_refundable_when_certificate_exists(self, cutoff_date): """ Assert that enrollment is not refundable once a certificat has been generated.""" cutoff_date.return_value = datetime.now(pytz.UTC) + timedelta(days=1) self.assertTrue(self.enrollment.refundable()) GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified' ) self.assertFalse(self.enrollment.refundable()) self.assertFalse( self.enrollment.refundable( user_already_has_certs_for=GeneratedCertificate.course_ids_with_certs_for_user(self.user) ) ) # Assert that can_refund overrides this and allows refund self.enrollment.can_refund = True self.assertTrue(self.enrollment.refundable()) self.assertTrue( self.enrollment.refundable( user_already_has_certs_for=GeneratedCertificate.course_ids_with_certs_for_user(self.user) ) )
def setUpClass(cls): super(CertificateGetTests, cls).setUpClass() cls.student = UserFactory() cls.student_no_cert = UserFactory() cls.course_1 = CourseFactory.create(org='edx', number='verified_1', display_name='Verified Course 1') cls.course_2 = CourseFactory.create(org='edx', number='verified_2', display_name='Verified Course 2') # certificate for the first course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.course_1.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88", ) # certificate for the second course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.course_2.id, status=CertificateStatuses.downloadable, mode='honor', download_url='www.gmail.com', grade="0.99", )
def test_user_with_passing_existing_downloadable_cert(self): # If user has already downloadable certificate then he can again re-generate the # the cert. GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified' ) analytics_patcher = patch('courseware.views.analytics') mock_tracker = analytics_patcher.start() self.addCleanup(analytics_patcher.stop) with patch('capa.xqueue_interface.XQueueInterface.send_to_queue') as mock_send_to_queue: mock_send_to_queue.return_value = (0, "Successfully queued") resp = self.client.post(self.url) self.assertEqual(resp.status_code, 200) #Verify Google Analytics event fired after generating certificate mock_tracker.track.assert_called_once_with( # pylint: disable=no-member self.student.id, # pylint: disable=no-member 'edx.bi.user.certificate.generate', { 'category': 'certificates', 'label': unicode(self.course.id) }, context={ 'Google Analytics': {'clientId': None} } ) mock_tracker.reset_mock()
def test_course_ids_with_certs_for_user(self): # Create one user with certs and one without student_no_certs = UserFactory() student_with_certs = UserFactory() student_with_certs.profile.allow_certificate = True student_with_certs.profile.save() # Set up a couple of courses course_1 = CourseFactory.create() course_2 = CourseFactory.create() # Generate certificates GeneratedCertificateFactory.create( user=student_with_certs, course_id=course_1.id, status=CertificateStatuses.downloadable, mode='honor') GeneratedCertificateFactory.create( user=student_with_certs, course_id=course_2.id, status=CertificateStatuses.downloadable, mode='honor') # User with no certs should return an empty set. self.assertSetEqual( GeneratedCertificate.course_ids_with_certs_for_user( student_no_certs), set()) # User with certs should return a set with the two course_ids self.assertSetEqual( GeneratedCertificate.course_ids_with_certs_for_user( student_with_certs), {course_1.id, course_2.id})
def setUp(self): super(CertificatesRestApiTest, self).setUp() self.student = UserFactory.create(password=USER_PASSWORD) self.student_no_cert = UserFactory.create(password=USER_PASSWORD) self.staff_user = UserFactory.create(password=USER_PASSWORD, is_staff=True) GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88") self.namespaced_url = 'certificates_api:v0:certificates:detail' # create a configuration for django-oauth-toolkit (DOT) dot_app_user = UserFactory.create(password=USER_PASSWORD) dot_app = dot_models.Application.objects.create( name='test app', user=dot_app_user, client_type='confidential', authorization_grant_type='authorization-code', redirect_uris='http://localhost:8079/complete/edxorg/') self.dot_access_token = dot_models.AccessToken.objects.create( user=self.student, application=dot_app, expires=datetime.utcnow() + timedelta(weeks=1), scope='read write', token='16MGyP3OaQYHmpT1lK7Q6MMNAZsjwF')
def test_course_ids_with_certs_for_user(self): # Create one user with certs and one without student_no_certs = UserFactory() student_with_certs = UserFactory() student_with_certs.profile.allow_certificate = True student_with_certs.profile.save() # Set up a couple of courses course_1 = CourseFactory.create() course_2 = CourseFactory.create() # Generate certificates GeneratedCertificateFactory.create( user=student_with_certs, course_id=course_1.id, status=CertificateStatuses.downloadable, mode='honor' ) GeneratedCertificateFactory.create( user=student_with_certs, course_id=course_2.id, status=CertificateStatuses.downloadable, mode='honor' ) # User with no certs should return an empty set. self.assertSetEqual( GeneratedCertificate.course_ids_with_certs_for_user(student_no_certs), set() ) # User with certs should return a set with the two course_ids self.assertSetEqual( GeneratedCertificate.course_ids_with_certs_for_user(student_with_certs), {course_1.id, course_2.id} )
def test_linked_in_add_to_profile_btn_not_appearing_without_config(self): # Without linked-in config don't show Add Certificate to LinkedIn button self.client.login(username="******", password="******") CourseModeFactory.create(course_id=self.course.id, mode_slug='verified', mode_display_name='verified', expiration_datetime=datetime.now(pytz.UTC) - timedelta(days=1)) CourseEnrollment.enroll(self.user, self.course.id, mode='honor') self.course.start = datetime.now(pytz.UTC) - timedelta(days=2) self.course.end = datetime.now(pytz.UTC) - timedelta(days=1) self.course.display_name = u"Omega" self.course = self.update_course(self.course, self.user.id) download_url = 'www.edx.org' GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='honor', grade='67', download_url=download_url) response = self.client.get(reverse('dashboard')) self.assertEquals(response.status_code, 200) self.assertNotIn('Add Certificate to LinkedIn', response.content) response_url = 'http://www.linkedin.com/profile/add?_ed=' self.assertNotContains(response, response_url)
def _create_user_data(self, user_enroll_mode, has_passed, whitelisted, is_embargoed, verification_status, certificate_status, certificate_mode): """ Create user data to be used during grade report generation. """ user = self.create_student('u1', mode=user_enroll_mode) if has_passed: self.submit_student_answer('u1', 'test_problem', ['choice_1']) CertificateWhitelistFactory.create(user=user, course_id=self.course.id, whitelist=whitelisted) self.user_is_embargoed(user, is_embargoed) if user_enroll_mode in CourseMode.VERIFIED_MODES: SoftwareSecurePhotoVerificationFactory.create(user=user, status=verification_status) GeneratedCertificateFactory.create( user=user, course_id=self.course.id, status=certificate_status, mode=certificate_mode ) return user
def test_certificate_exception_removed_successfully(self): """ Test certificates exception removal api endpoint returns success status when called with valid course key and certificate exception id """ GeneratedCertificateFactory.create( user=self.user2, course_id=self.course.id, status=CertificateStatuses.downloadable, grade='1.0' ) response = self.client.post( self.url, data=json.dumps(self.certificate_exception_in_db), content_type='application/json', REQUEST_METHOD='DELETE' ) # Assert successful request processing self.assertEqual(response.status_code, 204) # Verify that certificate exception successfully removed from CertificateWhitelist and GeneratedCertificate with self.assertRaises(ObjectDoesNotExist): CertificateWhitelist.objects.get(user=self.user2, course_id=self.course.id) GeneratedCertificate.objects.get( user=self.user2, course_id=self.course.id, status__not=CertificateStatuses.unavailable )
def setUp(self): super(CertificatesRestApiTest, self).setUp() self.student = UserFactory.create(password=USER_PASSWORD) self.student_no_cert = UserFactory.create(password=USER_PASSWORD) self.staff_user = UserFactory.create(password=USER_PASSWORD, is_staff=True) GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88" ) self.namespaced_url = 'certificates_api:v0:certificates:detail' # create a configuration for django-oauth-toolkit (DOT) dot_app_user = UserFactory.create(password=USER_PASSWORD) dot_app = dot_models.Application.objects.create( name='test app', user=dot_app_user, client_type='confidential', authorization_grant_type='authorization-code', redirect_uris='http://localhost:8079/complete/edxorg/' ) self.dot_access_token = dot_models.AccessToken.objects.create( user=self.student, application=dot_app, expires=datetime.utcnow() + timedelta(weeks=1), scope='read write', token='16MGyP3OaQYHmpT1lK7Q6MMNAZsjwF' )
def setUpClass(cls): super(CertificateGetTests, cls).setUpClass() cls.student = UserFactory() cls.student_no_cert = UserFactory() cls.uuid = uuid.uuid4().hex cls.web_cert_course = CourseFactory.create( org='edx', number='verified_1', display_name='Verified Course 1', cert_html_view_enabled=True) cls.pdf_cert_course = CourseFactory.create( org='edx', number='verified_2', display_name='Verified Course 2', cert_html_view_enabled=False) # certificate for the first course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.web_cert_course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88", verify_uuid=cls.uuid, ) # certificate for the second course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.pdf_cert_course.id, status=CertificateStatuses.downloadable, mode='honor', download_url='www.gmail.com', grade="0.99", verify_uuid=cls.uuid, )
def test_linked_in_add_to_profile_btn_not_appearing_without_config(self): # Without linked-in config don't show Add Certificate to LinkedIn button self.client.login(username="******", password="******") CourseModeFactory.create( course_id=self.course.id, mode_slug='verified', mode_display_name='verified', expiration_datetime=datetime.now(pytz.UTC) - timedelta(days=1) ) CourseEnrollment.enroll(self.user, self.course.id, mode='honor') self.course.start = datetime.now(pytz.UTC) - timedelta(days=2) self.course.end = datetime.now(pytz.UTC) - timedelta(days=1) self.course.display_name = u"Omega" self.course = self.update_course(self.course, self.user.id) download_url = 'www.edx.org' GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='honor', grade='67', download_url=download_url ) response = self.client.get(reverse('dashboard')) self.assertEquals(response.status_code, 200) self.assertNotIn('Add Certificate to LinkedIn', response.content) response_url = 'http://www.linkedin.com/profile/add?_ed=' self.assertNotContains(response, escape(response_url))
def test_certificate_regeneration_success(self): """ Test certificate regeneration is successful when accessed with 'certificate_statuses' present in GeneratedCertificate table. """ # Create a generated Certificate of some user with status 'downloadable' GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='honor' ) # Login the client and access the url with 'certificate_statuses' self.client.login(username=self.global_staff.username, password='******') url = reverse('start_certificate_regeneration', kwargs={'course_id': unicode(self.course.id)}) response = self.client.post(url, data={'certificate_statuses': [CertificateStatuses.downloadable]}) # Assert 200 status code in response self.assertEqual(response.status_code, 200) res_json = json.loads(response.content) # Assert request is successful self.assertTrue(res_json['success']) # Assert success message self.assertEqual( res_json['message'], u'Certificate regeneration task has been started. You can view the status of the generation task in ' u'the "Pending Tasks" section.' )
def setUpClass(cls): super(CertificateGetTests, cls).setUpClass() cls.student = UserFactory() cls.student_no_cert = UserFactory() cls.course_1 = CourseFactory.create( org='edx', number='verified_1', display_name='Verified Course 1' ) cls.course_2 = CourseFactory.create( org='edx', number='verified_2', display_name='Verified Course 2' ) # certificate for the first course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.course_1.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88", ) # certificate for the second course GeneratedCertificateFactory.create( user=cls.student, course_id=cls.course_2.id, status=CertificateStatuses.downloadable, mode='honor', download_url='www.gmail.com', grade="0.99", )
def test_course_milestone_collected(self): seed_milestone_relationship_types() student = UserFactory() course = CourseFactory.create(org='edx', number='998', display_name='Test Course') pre_requisite_course = CourseFactory.create( org='edx', number='999', display_name='Pre requisite Course') # set pre-requisite course set_prerequisite_courses(course.id, [unicode(pre_requisite_course.id)]) # get milestones collected by user before completing the pre-requisite course completed_milestones = milestones_achieved_by_user( student, unicode(pre_requisite_course.id)) self.assertEqual(len(completed_milestones), 0) GeneratedCertificateFactory.create( user=student, course_id=pre_requisite_course.id, status=CertificateStatuses.generating, mode='verified') # get milestones collected by user after user has completed the pre-requisite course completed_milestones = milestones_achieved_by_user( student, unicode(pre_requisite_course.id)) self.assertEqual(len(completed_milestones), 1) self.assertEqual(completed_milestones[0]['namespace'], unicode(pre_requisite_course.id))
def test_cert_status_with_generating(self): GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.generating, mode="verified" ) self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), {"is_downloadable": False, "is_generating": True, "download_url": None, "uuid": None}, )
def test_user_with_passing_existing_generating_cert(self): # If user has passing grade but also has existing generating cert # then json will return cert generating message with bad request code GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.generating, mode="verified" ) resp = self.client.post(self.url) self.assertEqual(resp.status_code, HttpResponseBadRequest.status_code) self.assertIn("Certificate is being created.", resp.content)
def test_certificate_honor_stats(self): GeneratedCertificateFactory(course_id=self.course.id, user=self.user, status=CertificateStatuses.notpassing) GeneratedCertificateFactory(course_id=self.course.id, user=UserFactory(), status=CertificateStatuses.downloadable) certificate_stats = stats.CertificateStats(unicode(self.course.id)) self.assertEqual(certificate_stats.not_passing(), 1) self.assertEqual(certificate_stats.passing(), 1) self.assertEqual(certificate_stats.total(), 2)
def test_user_with_passing_existing_downloadable_cert(self): # If user has passing grade but also has existing downloadable cert # then json will return cert generating message with bad request code GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified') resp = self.client.post(self.url) self.assertEqual(resp.status_code, HttpResponseBadRequest.status_code) self.assertIn("Creating certificate", resp.content)
def setUp(self): super(EligibleCertificateManagerTest, self).setUp() self.user = UserFactory() self.eligible_cert = GeneratedCertificateFactory.create( status=CertificateStatuses.downloadable, user=self.user, course_id=self.courses[0].id # pylint: disable=no-member ) self.ineligible_cert = GeneratedCertificateFactory.create( status=CertificateStatuses.audit_passing, user=self.user, course_id=self.courses[1].id # pylint: disable=no-member )
def setUp(self): super(EligibleCertificateManagerTest, self).setUp() self.user = UserFactory() self.eligible_cert = GeneratedCertificateFactory.create( eligible_for_certificate=True, user=self.user, course_id=self.courses[0].id # pylint: disable=no-member ) self.ineligible_cert = GeneratedCertificateFactory.create( eligible_for_certificate=False, user=self.user, course_id=self.courses[1].id # pylint: disable=no-member )
def test_with_downloadable_pdf_cert(self): GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode="verified", download_url="www.google.com", ) self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), {"is_downloadable": True, "is_generating": False, "download_url": "www.google.com"}, )
def test_view_certificate_link(self): """ If certificate web view is enabled then certificate web view button should appear for user who certificate is available/generated """ GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, download_url="http://www.example.com/certificate.pdf", mode='honor' ) # Enable the feature, but do not enable it for this course CertificateGenerationConfiguration(enabled=True).save() # Enable certificate generation for this course certs_api.set_cert_generation_enabled(self.course.id, True) #course certificate configurations certificates = [ { 'id': 1, 'name': 'Name 1', 'description': 'Description 1', 'course_title': 'course_title_1', 'org_logo_path': '/t4x/orgX/testX/asset/org-logo-1.png', 'signatories': [], 'version': 1, 'is_active': True } ] self.course.certificates = {'certificates': certificates} self.course.save() self.store.update_item(self.course, self.user.id) resp = views.progress(self.request, course_id=unicode(self.course.id)) self.assertContains(resp, u"View Certificate") self.assertContains(resp, u"You can now view your certificate") self.assertContains(resp, certs_api.get_certificate_url(user_id=self.user.id, course_id=self.course.id)) # when course certificate is not active certificates[0]['is_active'] = False self.store.update_item(self.course, self.user.id) resp = views.progress(self.request, course_id=unicode(self.course.id)) self.assertNotContains(resp, u"View Your Certificate") self.assertNotContains(resp, u"You can now view your certificate") self.assertContains(resp, u"We're creating your certificate.")
def test_user_with_passing_existing_downloadable_cert(self): # If user has already downloadable certificate # then json will return cert generating message with bad request code GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified' ) resp = self.client.post(self.url) self.assertEqual(resp.status_code, HttpResponseBadRequest.status_code) self.assertIn("Certificate has already been created.", resp.content)
def test_user_cert_status_with_error(self): GeneratedCertificateFactory.create(user=self.student, course_id=self.course.id, status=CertificateStatuses.error, mode='verified') self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), { 'is_downloadable': False, 'is_generating': True, 'download_url': None })
def test_certificate(self): self.login_and_enroll() certificate_url = "http://test_certificate_url" GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url=certificate_url, ) response = self.api_response() certificate_data = response.data[0]['certificate'] self.assertEquals(certificate_data['url'], certificate_url)
def test_certificate(self): self.login_and_enroll() certificate_url = "http://test_certificate_url" GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode="verified", download_url=certificate_url, ) response = self.api_response() certificate_data = response.data[0]["certificate"] # pylint: disable=no-member self.assertEquals(certificate_data["url"], certificate_url)
def test_refundable_when_certificate_exists(self): """ Assert that enrollment is not refundable once a certificat has been generated.""" self.assertTrue(self.enrollment.refundable()) GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified') self.assertFalse(self.enrollment.refundable()) # Assert that can_refund overrides this and allows refund self.enrollment.can_refund = True self.assertTrue(self.enrollment.refundable())
def test_certificate(self): self.login_and_enroll() certificate_url = "http://test_certificate_url" GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url=certificate_url, ) response = self.api_response() certificate_data = response.data[0]['certificate'] # pylint: disable=no-member self.assertEquals(certificate_data['url'], certificate_url)
def test_linked_in_add_to_profile_btn_with_certificate(self): # If user has a certificate with valid linked-in config then Add Certificate to LinkedIn button # should be visible. and it has URL value with valid parameters. self.client.login(username="******", password="******") LinkedInAddToProfileConfiguration.objects.create( company_identifier='0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9', enabled=True ) CourseModeFactory.create( course_id=self.course.id, mode_slug='verified', mode_display_name='verified', expiration_datetime=datetime.now(pytz.UTC) - timedelta(days=1) ) self.course.certificate_available_date = datetime.now(pytz.UTC) - timedelta(days=1) CourseEnrollment.enroll(self.user, self.course.id, mode='honor') self.course.start = datetime.now(pytz.UTC) - timedelta(days=2) self.course.end = datetime.now(pytz.UTC) - timedelta(days=1) self.course.display_name = u"Omega" self.course = self.update_course(self.course, self.user.id) download_url = 'www.edx.org' GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='honor', grade='67', download_url=download_url ) response = self.client.get(reverse('dashboard')) self.assertEquals(response.status_code, 200) self.assertIn('Add Certificate to LinkedIn', response.content) expected_url = ( u'http://www.linkedin.com/profile/add' u'?_ed=0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9&' u'pfCertificationName={platform}+Honor+Code+Certificate+for+Omega&' u'pfCertificationUrl=www.edx.org&' u'source=o' ).format(platform=quote(settings.PLATFORM_NAME.encode('utf-8'))) self.assertContains(response, escape(expected_url))
def test_generate_user_certificates_with_unverified_cert_status(self): """ Generate user certificate will not raise exception in case of certificate is None. """ # generate certificate with unverified status. GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.unverified, mode='verified' ) with mock_passing_grade(): with self._mock_queue(is_successful=False): status = certs_api.generate_user_certificates(self.student, self.course.id) self.assertEqual(status, None)
def test_regen_audit_certs_eligibility(self): """ Test that existing audit certificates remain eligible even if cert generation is re-run. """ # Create an existing audit enrollment and certificate CourseEnrollmentFactory( user=self.user_2, course_id=self.course.id, is_active=True, mode=CourseMode.AUDIT, ) GeneratedCertificateFactory( user=self.user_2, course_id=self.course.id, grade='1.0', status=CertificateStatuses.downloadable, mode=GeneratedCertificate.MODES.audit, ) # Run grading/cert generation again with patch('courseware.grades.grade', Mock(return_value={'grade': 'Pass', 'percent': 0.75})): with patch.object(XQueueInterface, 'send_to_queue') as mock_send: mock_send.return_value = (0, None) self.xqueue.add_cert(self.user_2, self.course.id) self.assertEqual( GeneratedCertificate.objects.get(user=self.user_2, course_id=self.course.id).status, # pylint: disable=no-member CertificateStatuses.generating )
def test_refundable_when_certificate_exists(self): CourseModeFactory.create( course_id=self.course.id, mode_slug="verified", mode_display_name="Verified", expiration_datetime=datetime.now(pytz.UTC) + timedelta(days=1), ) enrollment = CourseEnrollment.enroll(self.user, self.course.id, mode="verified") self.assertTrue(enrollment.refundable()) GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode="verified" ) self.assertFalse(enrollment.refundable())
def test_user_with_downloadable_cert(self): GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com') self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), { 'is_downloadable': True, 'is_generating': False, 'download_url': 'www.google.com' })
def test_regen_audit_certs_eligibility(self, status, created_date, grade, expected_status): """ Test that existing audit certificates remain eligible even if cert generation is re-run. """ # Create an existing audit enrollment and certificate CourseEnrollmentFactory( user=self.user_2, course_id=self.course.id, is_active=True, mode=CourseMode.AUDIT, ) with freezegun.freeze_time(created_date): GeneratedCertificateFactory( user=self.user_2, course_id=self.course.id, grade='1.0', status=status, mode=GeneratedCertificate.MODES.audit, ) # Run grading/cert generation again with mock_passing_grade(grade_pass=grade): with patch.object(XQueueInterface, 'send_to_queue') as mock_send: mock_send.return_value = (0, None) self.xqueue.add_cert(self.user_2, self.course.id) self.assertEqual( GeneratedCertificate.objects.get(user=self.user_2, course_id=self.course.id).status, # pylint: disable=no-member expected_status)
def test_refundable_when_certificate_exists(self): """ Assert that enrollment is not refundable once a certificat has been generated.""" self.assertTrue(self.enrollment.refundable()) GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified' ) self.assertFalse(self.enrollment.refundable()) # Assert that can_refund overrides this and allows refund self.enrollment.can_refund = True self.assertTrue(self.enrollment.refundable())
def test_user_cert_status_with_error(self): GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.error, mode='verified' ) self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), { 'is_downloadable': False, 'is_generating': True, 'download_url': None } )
def setUp(self): super(CertificatesViewsTests, self).setUp() self.client = Client() self.course = CourseFactory.create( org='testorg', number='run1', display_name='refundable course' ) self.course_id = self.course.location.course_key self.user = UserFactory.create( email='*****@*****.**', username='******', password='******' ) self.user.profile.name = "Joe User" self.user.profile.save() self.client.login(username=self.user.username, password='******') self.request = RequestFactory().request() self.cert = GeneratedCertificateFactory.create( user=self.user, course_id=self.course_id, download_uuid=uuid4(), download_url="http://www.example.com/certificates/download", grade="0.95", key='the_key', distinction=True, status='downloadable', mode='honor', name=self.user.profile.name, ) CourseEnrollmentFactory.create( user=self.user, course_id=self.course_id ) CertificateHtmlViewConfigurationFactory.create() LinkedInAddToProfileConfigurationFactory.create()
def test_linked_in_add_to_profile_btn_with_certificate(self): # If user has a certificate with valid linked-in config then Add Certificate to LinkedIn button # should be visible. and it has URL value with valid parameters. self.client.login(username="******", password="******") LinkedInAddToProfileConfiguration.objects.create( company_identifier='0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9', enabled=True ) CourseModeFactory.create( course_id=self.course.id, mode_slug='verified', mode_display_name='verified', expiration_datetime=datetime.now(pytz.UTC) - timedelta(days=1) ) CourseEnrollment.enroll(self.user, self.course.id, mode='honor') self.course.start = datetime.now(pytz.UTC) - timedelta(days=2) self.course.end = datetime.now(pytz.UTC) - timedelta(days=1) self.course.display_name = u"Omega" self.course = self.update_course(self.course, self.user.id) download_url = 'www.edx.org' GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='honor', grade='67', download_url=download_url ) response = self.client.get(reverse('dashboard')) self.assertEquals(response.status_code, 200) self.assertIn('Add Certificate to LinkedIn', response.content) expected_url = ( u'http://www.linkedin.com/profile/add' u'?_ed=0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9&' u'pfCertificationName={platform}+Honor+Code+Certificate+for+Omega&' u'pfCertificationUrl=www.edx.org&' u'source=o' ).format(platform=quote(settings.PLATFORM_NAME.encode('utf-8'))) self.assertContains(response, escape(expected_url))
def setUp(self): super(CertificatesRestApiTest, self).setUp() self.student = UserFactory.create(password='******') self.student_no_cert = UserFactory.create(password='******') self.staff_user = UserFactory.create(password='******', is_staff=True) GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com', grade="0.88" ) self.namespaced_url = 'certificates_api:v0:certificates:detail'
def test_certificate_regeneration_error(self): """ Test certificate regeneration errors out when accessed with either empty list of 'certificate_statuses' or the 'certificate_statuses' that are not present in GeneratedCertificate table. """ # Create a dummy course and GeneratedCertificate with the same status as the one we will use to access # 'start_certificate_regeneration' but their error message should be displayed as GeneratedCertificate # belongs to a different course dummy_course = CourseFactory.create() GeneratedCertificateFactory.create( user=self.user, course_id=dummy_course.id, status=CertificateStatuses.generating, mode='honor') # Login the client and access the url without 'certificate_statuses' self.client.login(username=self.global_staff.username, password='******') url = reverse('start_certificate_regeneration', kwargs={'course_id': unicode(self.course.id)}) response = self.client.post(url) # Assert 400 status code in response self.assertEqual(response.status_code, 400) res_json = json.loads(response.content) # Assert Error Message self.assertEqual( res_json['message'], u'Please select one or more certificate statuses that require certificate regeneration.' ) # Access the url passing 'certificate_statuses' that are not present in db url = reverse('start_certificate_regeneration', kwargs={'course_id': unicode(self.course.id)}) response = self.client.post( url, data={'certificate_statuses': [CertificateStatuses.generating]}) # Assert 400 status code in response self.assertEqual(response.status_code, 400) res_json = json.loads(response.content) # Assert Error Message self.assertEqual( res_json['message'], u'Please select certificate statuses from the list only.')
def _generate_cert(self, status): """ Dry method to generate certificate. """ return GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=status, mode='verified' )
def setUp(self): super(CertificateInvalidationTest, self).setUp() self.course = CourseFactory() self.user = UserFactory() self.course_id = self.course.id # pylint: disable=no-member self.certificate = GeneratedCertificateFactory.create( status=CertificateStatuses.downloadable, user=self.user, course_id=self.course_id )
def test_user_with_downloadable_cert(self): GeneratedCertificateFactory.create( user=self.student, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url='www.google.com' ) self.assertEqual( certs_api.certificate_downloadable_status(self.student, self.course.id), { 'is_downloadable': True, 'is_generating': False, 'download_url': 'www.google.com' } )
def setUp(self): super(CertificateInvalidationTest, self).setUp() self.course = CourseFactory() self.user = UserFactory() self.course_id = self.course.id # pylint: disable=no-member self.certificate = GeneratedCertificateFactory.create( status=CertificateStatuses.downloadable, user=self.user, course_id=self.course_id)
def test_linked_in_add_to_profile_btn_with_certificate(self): # If user has a certificate with valid linked-in config then Add Certificate to LinkedIn button # should be visible. and it has URL value with valid parameters. self.client.login(username="******", password="******") LinkedInAddToProfileConfiguration( company_identifier="0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9", enabled=True ).save() CourseModeFactory.create( course_id=self.course.id, mode_slug="verified", mode_display_name="verified", expiration_datetime=datetime.now(pytz.UTC) - timedelta(days=1), ) CourseEnrollment.enroll(self.user, self.course.id, mode="honor") self.course.start = datetime.now(pytz.UTC) - timedelta(days=2) self.course.end = datetime.now(pytz.UTC) - timedelta(days=1) self.course.display_name = u"Omega" self.course = self.update_course(self.course, self.user.id) download_url = "www.edx.org" GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode="honor", grade="67", download_url=download_url, ) response = self.client.get(reverse("dashboard")) self.assertEquals(response.status_code, 200) self.assertIn("Add Certificate to LinkedIn", response.content) expected_url = ( "http://www.linkedin.com/profile/add" "?_ed=0_mC_o2MizqdtZEmkVXjH4eYwMj4DnkCWrZP_D9&" "pfCertificationName=edX+Honor+Code+Certificate+for+Omega&" "pfCertificationUrl=www.edx.org&" "source=o" ) self.assertContains(response, expected_url)
def verify_pdf_certificate(self): """ Verifies the correct URL is returned in the response for PDF certificates. """ self.login_and_enroll() certificate_url = "http://test_certificate_url" GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified', download_url=certificate_url, ) response = self.api_response() certificate_data = response.data[0]['certificate'] self.assertEquals(certificate_data['url'], certificate_url)
def test_refundable_when_certificate_exists(self): CourseModeFactory.create(course_id=self.course.id, mode_slug='verified', mode_display_name='Verified', expiration_datetime=datetime.now(pytz.UTC) + timedelta(days=1)) enrollment = CourseEnrollment.enroll(self.user, self.course.id, mode='verified') self.assertTrue(enrollment.refundable()) GeneratedCertificateFactory.create( user=self.user, course_id=self.course.id, status=CertificateStatuses.downloadable, mode='verified') self.assertFalse(enrollment.refundable())