Make course ids and usage ids opaque to LMS and Studio [partial commit]
This commit adds the non-courseware lms/djangoapps and lms/lib. These keys are now objects with a limited interface, and the particular internal representation is managed by the data storage layer (the modulestore). For the LMS, there should be no outward-facing changes to the system. The keys are, for now, a change to internal representation only. For Studio, the new serialized form of the keys is used in urls, to allow for further migration in the future. Co-Author: Andy Armstrong <andya@edx.org> Co-Author: Christina Roberts <christina@edx.org> Co-Author: David Baumgold <db@edx.org> Co-Author: Diana Huang <dkh@edx.org> Co-Author: Don Mitchell <dmitchell@edx.org> Co-Author: Julia Hansbrough <julia@edx.org> Co-Author: Nimisha Asthagiri <nasthagiri@edx.org> Co-Author: Sarina Canelake <sarina@edx.org> [LMS-2370]
This commit is contained in:
@@ -12,12 +12,14 @@ from django.test import TestCase
|
||||
from nose.tools import raises
|
||||
from mock import Mock, patch
|
||||
from django.test.utils import override_settings
|
||||
from django.conf import settings
|
||||
from django.core.urlresolvers import reverse
|
||||
from django.http import HttpRequest, HttpResponse
|
||||
from django_comment_common.models import FORUM_ROLE_COMMUNITY_TA, Role
|
||||
from django_comment_common.utils import seed_permissions_roles
|
||||
from django.core import mail
|
||||
from django.utils.timezone import utc
|
||||
from django.test import RequestFactory
|
||||
|
||||
from django.contrib.auth.models import User
|
||||
from courseware.tests.modulestore_config import TEST_DATA_MIXED_MODULESTORE
|
||||
@@ -27,6 +29,7 @@ from xmodule.modulestore.tests.factories import CourseFactory, ItemFactory
|
||||
from student.tests.factories import UserFactory
|
||||
from courseware.tests.factories import StaffFactory, InstructorFactory, BetaTesterFactory
|
||||
from student.roles import CourseBetaTesterRole
|
||||
from microsite_configuration import microsite
|
||||
|
||||
from student.models import CourseEnrollment, CourseEnrollmentAllowed
|
||||
from courseware.models import StudentModule
|
||||
@@ -35,10 +38,11 @@ from courseware.models import StudentModule
|
||||
import instructor_task.api
|
||||
from instructor.access import allow_access
|
||||
import instructor.views.api
|
||||
from instructor.views.api import _split_input_list, _msk_from_problem_urlname, common_exceptions_400
|
||||
from instructor.views.api import _split_input_list, common_exceptions_400
|
||||
from instructor_task.api_helper import AlreadyRunningError
|
||||
from xmodule.modulestore.locations import SlashSeparatedCourseKey
|
||||
|
||||
from .test_tools import get_extended_due
|
||||
from .test_tools import msk_from_problem_urlname, get_extended_due
|
||||
|
||||
|
||||
@common_exceptions_400
|
||||
@@ -108,14 +112,15 @@ class TestInstructorAPIDenyLevels(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.user = UserFactory.create()
|
||||
CourseEnrollment.enroll(self.user, self.course.id)
|
||||
|
||||
self.problem_urlname = 'robot-some-problem-urlname'
|
||||
self.problem_location = msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
'robot-some-problem-urlname'
|
||||
)
|
||||
self.problem_urlname = str(self.problem_location)
|
||||
_module = StudentModule.objects.create(
|
||||
student=self.user,
|
||||
course_id=self.course.id,
|
||||
module_state_key=_msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
self.problem_urlname
|
||||
),
|
||||
module_id=self.problem_location,
|
||||
state=json.dumps({'attempts': 10}),
|
||||
)
|
||||
|
||||
@@ -153,13 +158,11 @@ class TestInstructorAPIDenyLevels(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
status_code: expected HTTP status code response
|
||||
msg: message to display if assertion fails.
|
||||
"""
|
||||
url = reverse(endpoint, kwargs={'course_id': self.course.id})
|
||||
if endpoint in 'send_email':
|
||||
url = reverse(endpoint, kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
if endpoint in ['send_email']:
|
||||
response = self.client.post(url, args)
|
||||
else:
|
||||
response = self.client.get(url, args)
|
||||
print endpoint
|
||||
print response
|
||||
self.assertEqual(
|
||||
response.status_code,
|
||||
status_code,
|
||||
@@ -192,7 +195,7 @@ class TestInstructorAPIDenyLevels(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
"""
|
||||
Ensure that a staff member can't access instructor endpoints.
|
||||
"""
|
||||
staff_member = StaffFactory(course=self.course.location)
|
||||
staff_member = StaffFactory(course=self.course.id)
|
||||
CourseEnrollment.enroll(staff_member, self.course.id)
|
||||
self.client.login(username=staff_member.username, password='test')
|
||||
# Try to promote to forums admin - not working
|
||||
@@ -221,7 +224,7 @@ class TestInstructorAPIDenyLevels(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
"""
|
||||
Ensure that an instructor member can access all endpoints.
|
||||
"""
|
||||
inst = InstructorFactory(course=self.course.location)
|
||||
inst = InstructorFactory(course=self.course.id)
|
||||
CourseEnrollment.enroll(inst, self.course.id)
|
||||
self.client.login(username=inst.username, password='test')
|
||||
|
||||
@@ -257,8 +260,9 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
job of test_enrollment. This tests the response and action switch.
|
||||
"""
|
||||
def setUp(self):
|
||||
self.request = RequestFactory().request()
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.enrolled_student = UserFactory(username='EnrolledStudent', first_name='Enrolled', last_name='Student')
|
||||
@@ -276,26 +280,41 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.notregistered_email = 'robot-not-an-email-yet@robot.org'
|
||||
self.assertEqual(User.objects.filter(email=self.notregistered_email).count(), 0)
|
||||
|
||||
# Email URL values
|
||||
self.site_name = microsite.get_value(
|
||||
'SITE_NAME',
|
||||
settings.SITE_NAME
|
||||
)
|
||||
self.registration_url = 'https://{}/register'.format(self.site_name)
|
||||
self.about_url = 'https://{}/courses/MITx/999/Robot_Super_Course/about'.format(self.site_name)
|
||||
self.course_url = 'https://{}/courses/MITx/999/Robot_Super_Course/'.format(self.site_name)
|
||||
|
||||
# uncomment to enable enable printing of large diffs
|
||||
# from failed assertions in the event of a test failure.
|
||||
# (comment because pylint C0103)
|
||||
# self.maxDiff = None
|
||||
|
||||
def tearDown(self):
|
||||
"""
|
||||
Undo all patches.
|
||||
"""
|
||||
patch.stopall()
|
||||
|
||||
def test_missing_params(self):
|
||||
""" Test missing all query parameters. """
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_bad_action(self):
|
||||
""" Test with an invalid action. """
|
||||
action = 'robot-not-an-action'
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.enrolled_student.email, 'action': action})
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_invalid_email(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': 'percivaloctavius@', 'action': 'enroll', 'email_students': False})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -315,7 +334,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(res_json, expected)
|
||||
|
||||
def test_invalid_username(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': 'percivaloctavius', 'action': 'enroll', 'email_students': False})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -335,7 +354,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(res_json, expected)
|
||||
|
||||
def test_enroll_with_username(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.username, 'action': 'enroll', 'email_students': False})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -366,7 +385,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(res_json, expected)
|
||||
|
||||
def test_enroll_without_email(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'enroll', 'email_students': False})
|
||||
print "type(self.notenrolled_student.email): {}".format(type(self.notenrolled_student.email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -405,7 +424,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(len(mail.outbox), 0)
|
||||
|
||||
def test_enroll_with_email(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'enroll', 'email_students': True})
|
||||
print "type(self.notenrolled_student.email): {}".format(type(self.notenrolled_student.email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -452,12 +471,14 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
"at edx.org by a member of the course staff. "
|
||||
"The course should now appear on your edx.org dashboard.\n\n"
|
||||
"To start accessing course materials, please visit "
|
||||
"https://edx.org/courses/MITx/999/Robot_Super_Course/\n\n----\n"
|
||||
"This email was automatically sent from edx.org to NotEnrolled Student"
|
||||
"{course_url}\n\n----\n"
|
||||
"This email was automatically sent from edx.org to NotEnrolled Student".format(
|
||||
course_url=self.course_url
|
||||
)
|
||||
)
|
||||
|
||||
def test_enroll_with_email_not_registered(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -470,18 +491,20 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(
|
||||
mail.outbox[0].body,
|
||||
"Dear student,\n\nYou have been invited to join Robot Super Course at edx.org by a member of the course staff.\n\n"
|
||||
"To finish your registration, please visit https://edx.org/register and fill out the registration form "
|
||||
"To finish your registration, please visit {registration_url} and fill out the registration form "
|
||||
"making sure to use robot-not-an-email-yet@robot.org in the E-mail field.\n"
|
||||
"Once you have registered and activated your account, "
|
||||
"visit https://edx.org/courses/MITx/999/Robot_Super_Course/about to join the course.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org"
|
||||
"visit {about_url} to join the course.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org".format(
|
||||
registration_url=self.registration_url, about_url=self.about_url
|
||||
)
|
||||
)
|
||||
|
||||
@patch.dict(settings.FEATURES, {'ENABLE_MKTG_SITE': True})
|
||||
def test_enroll_email_not_registered_mktgsite(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
# Try with marketing site enabled
|
||||
with patch.dict('django.conf.settings.FEATURES', {'ENABLE_MKTG_SITE': True}):
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True})
|
||||
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(
|
||||
@@ -494,7 +517,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
)
|
||||
|
||||
def test_enroll_with_email_not_registered_autoenroll(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True, 'auto_enroll': True})
|
||||
print "type(self.notregistered_email): {}".format(type(self.notregistered_email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -508,14 +531,16 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(
|
||||
mail.outbox[0].body,
|
||||
"Dear student,\n\nYou have been invited to join Robot Super Course at edx.org by a member of the course staff.\n\n"
|
||||
"To finish your registration, please visit https://edx.org/register and fill out the registration form "
|
||||
"To finish your registration, please visit {registration_url} and fill out the registration form "
|
||||
"making sure to use robot-not-an-email-yet@robot.org in the E-mail field.\n"
|
||||
"Once you have registered and activated your account, you will see Robot Super Course listed on your dashboard.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org".format(
|
||||
registration_url=self.registration_url
|
||||
)
|
||||
)
|
||||
|
||||
def test_unenroll_without_email(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.enrolled_student.email, 'action': 'unenroll', 'email_students': False})
|
||||
print "type(self.enrolled_student.email): {}".format(type(self.enrolled_student.email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -554,7 +579,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(len(mail.outbox), 0)
|
||||
|
||||
def test_unenroll_with_email(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.enrolled_student.email, 'action': 'unenroll', 'email_students': True})
|
||||
print "type(self.enrolled_student.email): {}".format(type(self.enrolled_student.email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -605,7 +630,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
)
|
||||
|
||||
def test_unenroll_with_email_allowed_student(self):
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.allowed_email, 'action': 'unenroll', 'email_students': True})
|
||||
print "type(self.allowed_email): {}".format(type(self.allowed_email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -653,7 +678,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_enroll_with_email_not_registered_with_shib(self, mock_uses_shib):
|
||||
mock_uses_shib.return_value = True
|
||||
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -667,15 +692,19 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(
|
||||
mail.outbox[0].body,
|
||||
"Dear student,\n\nYou have been invited to join Robot Super Course at edx.org by a member of the course staff.\n\n"
|
||||
"To access the course visit https://edx.org/courses/MITx/999/Robot_Super_Course/about and register for the course.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org"
|
||||
"To access the course visit {about_url} and register for the course.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org".format(
|
||||
about_url=self.about_url
|
||||
)
|
||||
)
|
||||
|
||||
@patch('instructor.enrollment.uses_shib')
|
||||
@patch.dict(settings.FEATURES, {'ENABLE_MKTG_SITE': True})
|
||||
def test_enroll_email_not_registered_shib_mktgsite(self, mock_uses_shib):
|
||||
# Try with marketing site enabled and shib on
|
||||
mock_uses_shib.return_value = True
|
||||
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
# Try with marketing site enabled
|
||||
with patch.dict('django.conf.settings.FEATURES', {'ENABLE_MKTG_SITE': True}):
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True})
|
||||
@@ -692,7 +721,7 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
|
||||
mock_uses_shib.return_value = True
|
||||
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id})
|
||||
url = reverse('students_update_enrollment', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'enroll', 'email_students': True, 'auto_enroll': True})
|
||||
print "type(self.notregistered_email): {}".format(type(self.notregistered_email))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -707,8 +736,10 @@ class TestInstructorAPIEnrollment(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(
|
||||
mail.outbox[0].body,
|
||||
"Dear student,\n\nYou have been invited to join Robot Super Course at edx.org by a member of the course staff.\n\n"
|
||||
"To access the course visit https://edx.org/courses/MITx/999/Robot_Super_Course/ and login.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org"
|
||||
"To access the course visit {course_url} and login.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to robot-not-an-email-yet@robot.org".format(
|
||||
course_url=self.course_url
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
@@ -719,20 +750,30 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
"""
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.beta_tester = BetaTesterFactory(course=self.course.location)
|
||||
self.beta_tester = BetaTesterFactory(course=self.course.id)
|
||||
CourseEnrollment.enroll(
|
||||
self.beta_tester,
|
||||
self.course.id
|
||||
)
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.id).has_user(self.beta_tester))
|
||||
|
||||
self.notenrolled_student = UserFactory(username='NotEnrolledStudent')
|
||||
|
||||
self.notregistered_email = 'robot-not-an-email-yet@robot.org'
|
||||
self.assertEqual(User.objects.filter(email=self.notregistered_email).count(), 0)
|
||||
|
||||
self.request = RequestFactory().request()
|
||||
|
||||
# Email URL values
|
||||
self.site_name = microsite.get_value(
|
||||
'SITE_NAME',
|
||||
settings.SITE_NAME
|
||||
)
|
||||
self.about_url = 'https://{}/courses/MITx/999/Robot_Super_Course/about'.format(self.site_name)
|
||||
|
||||
# uncomment to enable enable printing of large diffs
|
||||
# from failed assertions in the event of a test failure.
|
||||
# (comment because pylint C0103)
|
||||
@@ -740,14 +781,14 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
|
||||
def test_missing_params(self):
|
||||
""" Test missing all query parameters. """
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_bad_action(self):
|
||||
""" Test with an invalid action. """
|
||||
action = 'robot-not-an-action'
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.beta_tester.email, 'action': action})
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
@@ -763,7 +804,7 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
Additionally asserts no email was sent.
|
||||
"""
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.location).has_user(self.notenrolled_student))
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.id).has_user(self.notenrolled_student))
|
||||
# test the response data
|
||||
expected = {
|
||||
"action": "add",
|
||||
@@ -783,35 +824,35 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
self.assertEqual(len(mail.outbox), 0)
|
||||
|
||||
def test_add_notenrolled_email(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': False})
|
||||
self.add_notenrolled(response, self.notenrolled_student.email)
|
||||
self.assertFalse(CourseEnrollment.is_enrolled(self.notenrolled_student, self.course.id))
|
||||
|
||||
def test_add_notenrolled_email_autoenroll(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': False, 'auto_enroll': True})
|
||||
self.add_notenrolled(response, self.notenrolled_student.email)
|
||||
self.assertTrue(CourseEnrollment.is_enrolled(self.notenrolled_student, self.course.id))
|
||||
|
||||
def test_add_notenrolled_username(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.username, 'action': 'add', 'email_students': False})
|
||||
self.add_notenrolled(response, self.notenrolled_student.username)
|
||||
self.assertFalse(CourseEnrollment.is_enrolled(self.notenrolled_student, self.course.id))
|
||||
|
||||
def test_add_notenrolled_username_autoenroll(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.username, 'action': 'add', 'email_students': False, 'auto_enroll': True})
|
||||
self.add_notenrolled(response, self.notenrolled_student.username)
|
||||
self.assertTrue(CourseEnrollment.is_enrolled(self.notenrolled_student, self.course.id))
|
||||
|
||||
def test_add_notenrolled_with_email(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': True})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.location).has_user(self.notenrolled_student))
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.id).has_user(self.notenrolled_student))
|
||||
# test the response data
|
||||
expected = {
|
||||
"action": "add",
|
||||
@@ -837,23 +878,24 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
mail.outbox[0].body,
|
||||
u"Dear {0}\n\nYou have been invited to be a beta tester "
|
||||
"for Robot Super Course at edx.org by a member of the course staff.\n\n"
|
||||
"Visit https://edx.org/courses/MITx/999/Robot_Super_Course/about to join "
|
||||
"Visit {1} to join "
|
||||
"the course and begin the beta test.\n\n----\n"
|
||||
"This email was automatically sent from edx.org to {1}".format(
|
||||
"This email was automatically sent from edx.org to {2}".format(
|
||||
self.notenrolled_student.profile.name,
|
||||
self.about_url,
|
||||
self.notenrolled_student.email
|
||||
)
|
||||
)
|
||||
|
||||
def test_add_notenrolled_with_email_autoenroll(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(
|
||||
url,
|
||||
{'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': True, 'auto_enroll': True}
|
||||
)
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.location).has_user(self.notenrolled_student))
|
||||
self.assertTrue(CourseBetaTesterRole(self.course.id).has_user(self.notenrolled_student))
|
||||
# test the response data
|
||||
expected = {
|
||||
"action": "add",
|
||||
@@ -887,11 +929,11 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
)
|
||||
)
|
||||
|
||||
@patch.dict(settings.FEATURES, {'ENABLE_MKTG_SITE': True})
|
||||
def test_add_notenrolled_email_mktgsite(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
# Try with marketing site enabled
|
||||
with patch.dict('django.conf.settings.FEATURES', {'ENABLE_MKTG_SITE': True}):
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': True})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notenrolled_student.email, 'action': 'add', 'email_students': True})
|
||||
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertEqual(
|
||||
@@ -907,7 +949,7 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
|
||||
def test_enroll_with_email_not_registered(self):
|
||||
# User doesn't exist
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.notregistered_email, 'action': 'add', 'email_students': True})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
# test the response data
|
||||
@@ -928,11 +970,15 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
self.assertEqual(len(mail.outbox), 0)
|
||||
|
||||
def test_remove_without_email(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.beta_tester.email, 'action': 'remove', 'email_students': False})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
self.assertFalse(CourseBetaTesterRole(self.course.location).has_user(self.beta_tester))
|
||||
# Works around a caching bug which supposedly can't happen in prod. The instance here is not ==
|
||||
# the instance fetched from the email above which had its cache cleared
|
||||
if hasattr(self.beta_tester, '_roles'):
|
||||
del self.beta_tester._roles
|
||||
self.assertFalse(CourseBetaTesterRole(self.course.id).has_user(self.beta_tester))
|
||||
|
||||
# test the response data
|
||||
expected = {
|
||||
@@ -952,11 +998,15 @@ class TestInstructorAPIBulkBetaEnrollment(ModuleStoreTestCase, LoginEnrollmentTe
|
||||
self.assertEqual(len(mail.outbox), 0)
|
||||
|
||||
def test_remove_with_email(self):
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('bulk_beta_modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'identifiers': self.beta_tester.email, 'action': 'remove', 'email_students': True})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
self.assertFalse(CourseBetaTesterRole(self.course.location).has_user(self.beta_tester))
|
||||
# Works around a caching bug which supposedly can't happen in prod. The instance here is not ==
|
||||
# the instance fetched from the email above which had its cache cleared
|
||||
if hasattr(self.beta_tester, '_roles'):
|
||||
del self.beta_tester._roles
|
||||
self.assertFalse(CourseBetaTesterRole(self.course.id).has_user(self.beta_tester))
|
||||
|
||||
# test the response data
|
||||
expected = {
|
||||
@@ -1005,24 +1055,22 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
"""
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.other_instructor = UserFactory()
|
||||
allow_access(self.course, self.other_instructor, 'instructor')
|
||||
self.other_staff = UserFactory()
|
||||
allow_access(self.course, self.other_staff, 'staff')
|
||||
self.other_instructor = InstructorFactory(course=self.course.id)
|
||||
self.other_staff = StaffFactory(course=self.course.id)
|
||||
self.other_user = UserFactory()
|
||||
|
||||
def test_modify_access_noparams(self):
|
||||
""" Test missing all query parameters. """
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_modify_access_bad_action(self):
|
||||
""" Test with an invalid action parameter. """
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_staff.email,
|
||||
'rolename': 'staff',
|
||||
@@ -1032,7 +1080,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
|
||||
def test_modify_access_bad_role(self):
|
||||
""" Test with an invalid action parameter. """
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_staff.email,
|
||||
'rolename': 'robot-not-a-roll',
|
||||
@@ -1041,16 +1089,16 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_modify_access_allow(self):
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_instructor.email,
|
||||
'unique_student_identifier': self.other_user.email,
|
||||
'rolename': 'staff',
|
||||
'action': 'allow',
|
||||
})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_modify_access_allow_with_uname(self):
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_instructor.username,
|
||||
'rolename': 'staff',
|
||||
@@ -1059,7 +1107,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_modify_access_revoke(self):
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_staff.email,
|
||||
'rolename': 'staff',
|
||||
@@ -1068,7 +1116,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_modify_access_revoke_with_username(self):
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_staff.username,
|
||||
'rolename': 'staff',
|
||||
@@ -1077,7 +1125,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_modify_access_with_fake_user(self):
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': 'GandalfTheGrey',
|
||||
'rolename': 'staff',
|
||||
@@ -1094,7 +1142,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
def test_modify_access_with_inactive_user(self):
|
||||
self.other_user.is_active = False
|
||||
self.other_user.save() # pylint: disable=no-member
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_user.username,
|
||||
'rolename': 'beta',
|
||||
@@ -1110,7 +1158,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
|
||||
def test_modify_access_revoke_not_allowed(self):
|
||||
""" Test revoking access that a user does not have. """
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.other_staff.email,
|
||||
'rolename': 'instructor',
|
||||
@@ -1122,7 +1170,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
"""
|
||||
Test that an instructor cannot remove instructor privelages from themself.
|
||||
"""
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id})
|
||||
url = reverse('modify_access', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'unique_student_identifier': self.instructor.email,
|
||||
'rolename': 'instructor',
|
||||
@@ -1141,30 +1189,28 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
|
||||
def test_list_course_role_members_noparams(self):
|
||||
""" Test missing all query parameters. """
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_list_course_role_members_bad_rolename(self):
|
||||
""" Test with an invalid rolename parameter. """
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'rolename': 'robot-not-a-rolename',
|
||||
})
|
||||
print response
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_list_course_role_members_staff(self):
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'rolename': 'staff',
|
||||
})
|
||||
print response
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
# check response content
|
||||
expected = {
|
||||
'course_id': self.course.id,
|
||||
'course_id': self.course.id.to_deprecated_string(),
|
||||
'staff': [
|
||||
{
|
||||
'username': self.other_staff.username,
|
||||
@@ -1178,16 +1224,15 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
self.assertEqual(res_json, expected)
|
||||
|
||||
def test_list_course_role_members_beta(self):
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_course_role_members', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'rolename': 'beta',
|
||||
})
|
||||
print response
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
# check response content
|
||||
expected = {
|
||||
'course_id': self.course.id,
|
||||
'course_id': self.course.id.to_deprecated_string(),
|
||||
'beta': []
|
||||
}
|
||||
res_json = json.loads(response.content)
|
||||
@@ -1225,7 +1270,7 @@ class TestInstructorAPILevelsAccess(ModuleStoreTestCase, LoginEnrollmentTestCase
|
||||
Get unique_student_identifier, rolename and action and update forum role.
|
||||
"""
|
||||
|
||||
url = reverse('update_forum_role_membership', kwargs={'course_id': self.course.id})
|
||||
url = reverse('update_forum_role_membership', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(
|
||||
url,
|
||||
{
|
||||
@@ -1253,7 +1298,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
"""
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.students = [UserFactory() for _ in xrange(6)]
|
||||
@@ -1265,7 +1310,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
Test that some minimum of information is formatted
|
||||
correctly in the response to get_students_features.
|
||||
"""
|
||||
url = reverse('get_students_features', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_students_features', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {})
|
||||
res_json = json.loads(response.content)
|
||||
self.assertIn('students', res_json)
|
||||
@@ -1281,7 +1326,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
"""
|
||||
Test the CSV output for the anonymized user ids.
|
||||
"""
|
||||
url = reverse('get_anon_ids', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_anon_ids', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
with patch('instructor.views.api.unique_id_for_user') as mock_unique:
|
||||
mock_unique.return_value = '42'
|
||||
response = self.client.get(url, {})
|
||||
@@ -1291,7 +1336,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
self.assertTrue(body.endswith('"7","42"\n'))
|
||||
|
||||
def test_list_report_downloads(self):
|
||||
url = reverse('list_report_downloads', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_report_downloads', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
with patch('instructor_task.models.LocalFSReportStore.links_for') as mock_links_for:
|
||||
mock_links_for.return_value = [
|
||||
('mock_file_name_1', 'https://1.mock.url'),
|
||||
@@ -1317,7 +1362,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
self.assertEqual(res_json, expected_response)
|
||||
|
||||
def test_calculate_grades_csv_success(self):
|
||||
url = reverse('calculate_grades_csv', kwargs={'course_id': self.course.id})
|
||||
url = reverse('calculate_grades_csv', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
|
||||
with patch('instructor_task.api.submit_calculate_grades_csv') as mock_cal_grades:
|
||||
mock_cal_grades.return_value = True
|
||||
@@ -1326,7 +1371,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
self.assertIn(success_status, response.content)
|
||||
|
||||
def test_calculate_grades_csv_already_running(self):
|
||||
url = reverse('calculate_grades_csv', kwargs={'course_id': self.course.id})
|
||||
url = reverse('calculate_grades_csv', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
|
||||
with patch('instructor_task.api.submit_calculate_grades_csv') as mock_cal_grades:
|
||||
mock_cal_grades.side_effect = AlreadyRunningError()
|
||||
@@ -1339,7 +1384,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
Test that some minimum of information is formatted
|
||||
correctly in the response to get_students_features.
|
||||
"""
|
||||
url = reverse('get_students_features', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_students_features', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url + '/csv', {})
|
||||
self.assertEqual(response['Content-Type'], 'text/csv')
|
||||
|
||||
@@ -1348,13 +1393,13 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
Test that get_distribution lists available features
|
||||
when supplied no feature parameter.
|
||||
"""
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 200)
|
||||
res_json = json.loads(response.content)
|
||||
self.assertEqual(type(res_json['available_features']), list)
|
||||
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url + u'?feature=')
|
||||
self.assertEqual(response.status_code, 200)
|
||||
res_json = json.loads(response.content)
|
||||
@@ -1365,7 +1410,7 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
Test that get_distribution fails gracefully with
|
||||
an unavailable feature.
|
||||
"""
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'feature': 'robot-not-a-real-feature'})
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
@@ -1374,11 +1419,10 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
Test that get_distribution fails gracefully with
|
||||
an unavailable feature.
|
||||
"""
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_distribution', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'feature': 'gender'})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
res_json = json.loads(response.content)
|
||||
print res_json
|
||||
self.assertEqual(res_json['feature_results']['data']['m'], 6)
|
||||
self.assertEqual(res_json['feature_results']['choices_display_names']['m'], 'Male')
|
||||
self.assertEqual(res_json['feature_results']['data']['no_data'], 0)
|
||||
@@ -1386,39 +1430,35 @@ class TestInstructorAPILevelsDataDump(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
|
||||
def test_get_student_progress_url(self):
|
||||
""" Test that progress_url is in the successful response. """
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
url += "?unique_student_identifier={}".format(
|
||||
quote(self.students[0].email.encode("utf-8"))
|
||||
)
|
||||
print url
|
||||
response = self.client.get(url)
|
||||
print response
|
||||
self.assertEqual(response.status_code, 200)
|
||||
res_json = json.loads(response.content)
|
||||
self.assertIn('progress_url', res_json)
|
||||
|
||||
def test_get_student_progress_url_from_uname(self):
|
||||
""" Test that progress_url is in the successful response. """
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
url += "?unique_student_identifier={}".format(
|
||||
quote(self.students[0].username.encode("utf-8"))
|
||||
)
|
||||
print url
|
||||
response = self.client.get(url)
|
||||
print response
|
||||
self.assertEqual(response.status_code, 200)
|
||||
res_json = json.loads(response.content)
|
||||
self.assertIn('progress_url', res_json)
|
||||
|
||||
def test_get_student_progress_url_noparams(self):
|
||||
""" Test that the endpoint 404's without the required query params. """
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_get_student_progress_url_nostudent(self):
|
||||
""" Test that the endpoint 400's when requesting an unknown email. """
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id})
|
||||
url = reverse('get_student_progress_url', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url)
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
@@ -1434,42 +1474,42 @@ class TestInstructorAPIRegradeTask(ModuleStoreTestCase, LoginEnrollmentTestCase)
|
||||
"""
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.student = UserFactory()
|
||||
CourseEnrollment.enroll(self.student, self.course.id)
|
||||
|
||||
self.problem_urlname = 'robot-some-problem-urlname'
|
||||
self.problem_location = msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
'robot-some-problem-urlname'
|
||||
)
|
||||
self.problem_urlname = str(self.problem_location)
|
||||
|
||||
self.module_to_reset = StudentModule.objects.create(
|
||||
student=self.student,
|
||||
course_id=self.course.id,
|
||||
module_state_key=_msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
self.problem_urlname
|
||||
),
|
||||
module_id=self.problem_location,
|
||||
state=json.dumps({'attempts': 10}),
|
||||
)
|
||||
|
||||
def test_reset_student_attempts_deletall(self):
|
||||
""" Make sure no one can delete all students state on a problem. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'all_students': True,
|
||||
'delete_module': True,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_reset_student_attempts_single(self):
|
||||
""" Test reset single student attempts. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.email,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
# make sure problem attempts have been reset.
|
||||
changed_module = StudentModule.objects.get(pk=self.module_to_reset.pk)
|
||||
@@ -1482,89 +1522,82 @@ class TestInstructorAPIRegradeTask(ModuleStoreTestCase, LoginEnrollmentTestCase)
|
||||
@patch.object(instructor_task.api, 'submit_reset_problem_attempts_for_all_students')
|
||||
def test_reset_student_attempts_all(self, act):
|
||||
""" Test reset all student attempts. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'all_students': True,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTrue(act.called)
|
||||
|
||||
def test_reset_student_attempts_missingmodule(self):
|
||||
""" Test reset for non-existant problem. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': 'robot-not-a-real-module',
|
||||
'unique_student_identifier': self.student.email,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_reset_student_attempts_delete(self):
|
||||
""" Test delete single student state. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.email,
|
||||
'delete_module': True,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
# make sure the module has been deleted
|
||||
self.assertEqual(
|
||||
StudentModule.objects.filter(
|
||||
student=self.module_to_reset.student,
|
||||
course_id=self.module_to_reset.course_id,
|
||||
# module_state_key=self.module_to_reset.module_state_key,
|
||||
# module_id=self.module_to_reset.module_id,
|
||||
).count(),
|
||||
0
|
||||
)
|
||||
|
||||
def test_reset_student_attempts_nonsense(self):
|
||||
""" Test failure with both unique_student_identifier and all_students. """
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_student_attempts', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.email,
|
||||
'all_students': True,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
@patch.object(instructor_task.api, 'submit_rescore_problem_for_student')
|
||||
def test_rescore_problem_single(self, act):
|
||||
""" Test rescoring of a single student. """
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id})
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.email,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTrue(act.called)
|
||||
|
||||
@patch.object(instructor_task.api, 'submit_rescore_problem_for_student')
|
||||
def test_rescore_problem_single_from_uname(self, act):
|
||||
""" Test rescoring of a single student. """
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id})
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.username,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTrue(act.called)
|
||||
|
||||
@patch.object(instructor_task.api, 'submit_rescore_problem_for_all_students')
|
||||
def test_rescore_problem_all(self, act):
|
||||
""" Test rescoring for all students. """
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id})
|
||||
url = reverse('rescore_problem', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'problem_to_reset': self.problem_urlname,
|
||||
'all_students': True,
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTrue(act.called)
|
||||
|
||||
@@ -1578,7 +1611,7 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
"""
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
test_subject = u'\u1234 test subject'
|
||||
test_message = u'\u6824 test message'
|
||||
@@ -1589,13 +1622,13 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
}
|
||||
|
||||
def test_send_email_as_logged_in_instructor(self):
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, self.full_test_message)
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_send_email_but_not_logged_in(self):
|
||||
self.client.logout()
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, self.full_test_message)
|
||||
self.assertEqual(response.status_code, 403)
|
||||
|
||||
@@ -1603,7 +1636,7 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.client.logout()
|
||||
student = UserFactory()
|
||||
self.client.login(username=student.username, password='test')
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, self.full_test_message)
|
||||
self.assertEqual(response.status_code, 403)
|
||||
|
||||
@@ -1613,7 +1646,7 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertNotEqual(response.status_code, 200)
|
||||
|
||||
def test_send_email_no_sendto(self):
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, {
|
||||
'subject': 'test subject',
|
||||
'message': 'test message',
|
||||
@@ -1621,7 +1654,7 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_send_email_no_subject(self):
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, {
|
||||
'send_to': 'staff',
|
||||
'message': 'test message',
|
||||
@@ -1629,7 +1662,7 @@ class TestInstructorSendEmail(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.assertEqual(response.status_code, 400)
|
||||
|
||||
def test_send_email_no_message(self):
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id})
|
||||
url = reverse('send_email', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.post(url, {
|
||||
'send_to': 'staff',
|
||||
'subject': 'test subject',
|
||||
@@ -1700,20 +1733,22 @@ class TestInstructorAPITaskLists(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
self.student = UserFactory()
|
||||
CourseEnrollment.enroll(self.student, self.course.id)
|
||||
|
||||
self.problem_urlname = 'robot-some-problem-urlname'
|
||||
self.problem_location = msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
'robot-some-problem-urlname'
|
||||
)
|
||||
self.problem_urlname = str(self.problem_location)
|
||||
|
||||
self.module = StudentModule.objects.create(
|
||||
student=self.student,
|
||||
course_id=self.course.id,
|
||||
module_state_key=_msk_from_problem_urlname(
|
||||
self.course.id,
|
||||
self.problem_urlname
|
||||
),
|
||||
module_id=self.problem_location,
|
||||
state=json.dumps({'attempts': 10}),
|
||||
)
|
||||
mock_factory = MockCompletionInfo()
|
||||
@@ -1730,7 +1765,7 @@ class TestInstructorAPITaskLists(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_list_instructor_tasks_running(self, act):
|
||||
""" Test list of all running tasks. """
|
||||
act.return_value = self.tasks
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
mock_factory = MockCompletionInfo()
|
||||
with patch('instructor.views.api.get_task_completion_info') as mock_completion_info:
|
||||
mock_completion_info.side_effect = mock_factory.mock_get_task_completion_info
|
||||
@@ -1749,7 +1784,7 @@ class TestInstructorAPITaskLists(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_list_background_email_tasks(self, act):
|
||||
"""Test list of background email tasks."""
|
||||
act.return_value = self.tasks
|
||||
url = reverse('list_background_email_tasks', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_background_email_tasks', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
mock_factory = MockCompletionInfo()
|
||||
with patch('instructor.views.api.get_task_completion_info') as mock_completion_info:
|
||||
mock_completion_info.side_effect = mock_factory.mock_get_task_completion_info
|
||||
@@ -1768,12 +1803,12 @@ class TestInstructorAPITaskLists(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_list_instructor_tasks_problem(self, act):
|
||||
""" Test list task history for problem. """
|
||||
act.return_value = self.tasks
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
mock_factory = MockCompletionInfo()
|
||||
with patch('instructor.views.api.get_task_completion_info') as mock_completion_info:
|
||||
mock_completion_info.side_effect = mock_factory.mock_get_task_completion_info
|
||||
response = self.client.get(url, {
|
||||
'problem_urlname': self.problem_urlname,
|
||||
'problem_location_str': self.problem_urlname,
|
||||
})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
@@ -1789,12 +1824,12 @@ class TestInstructorAPITaskLists(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_list_instructor_tasks_problem_student(self, act):
|
||||
""" Test list task history for problem AND student. """
|
||||
act.return_value = self.tasks
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id})
|
||||
url = reverse('list_instructor_tasks', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
mock_factory = MockCompletionInfo()
|
||||
with patch('instructor.views.api.get_task_completion_info') as mock_completion_info:
|
||||
mock_completion_info.side_effect = mock_factory.mock_get_task_completion_info
|
||||
response = self.client.get(url, {
|
||||
'problem_urlname': self.problem_urlname,
|
||||
'problem_location_str': self.problem_urlname,
|
||||
'unique_student_identifier': self.student.email,
|
||||
})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
@@ -1831,7 +1866,7 @@ class TestInstructorAPIAnalyticsProxy(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
|
||||
def setUp(self):
|
||||
self.course = CourseFactory.create()
|
||||
self.instructor = InstructorFactory(course=self.course.location)
|
||||
self.instructor = InstructorFactory(course=self.course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
@patch.object(instructor.views.api.requests, 'get')
|
||||
@@ -1839,18 +1874,17 @@ class TestInstructorAPIAnalyticsProxy(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
""" Test legacy analytics proxy url generation. """
|
||||
act.return_value = self.FakeProxyResponse()
|
||||
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id})
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'aname': 'ProblemGradeDistribution'
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
# check request url
|
||||
expected_url = "{url}get?aname={aname}&course_id={course_id}&apikey={api_key}".format(
|
||||
expected_url = "{url}get?aname={aname}&course_id={course_id!s}&apikey={api_key}".format(
|
||||
url="http://robotanalyticsserver.netbot:900/",
|
||||
aname="ProblemGradeDistribution",
|
||||
course_id=self.course.id,
|
||||
course_id=self.course.id.to_deprecated_string(),
|
||||
api_key="robot_api_key",
|
||||
)
|
||||
act.assert_called_once_with(expected_url)
|
||||
@@ -1862,11 +1896,10 @@ class TestInstructorAPIAnalyticsProxy(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
"""
|
||||
act.return_value = self.FakeProxyResponse()
|
||||
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id})
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'aname': 'ProblemGradeDistribution'
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
# check response
|
||||
@@ -1879,11 +1912,10 @@ class TestInstructorAPIAnalyticsProxy(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
""" Test proxy when server reponds with failure. """
|
||||
act.return_value = self.FakeBadProxyResponse()
|
||||
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id})
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'aname': 'ProblemGradeDistribution'
|
||||
})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 500)
|
||||
|
||||
@patch.object(instructor.views.api.requests, 'get')
|
||||
@@ -1891,9 +1923,8 @@ class TestInstructorAPIAnalyticsProxy(ModuleStoreTestCase, LoginEnrollmentTestCa
|
||||
""" Test proxy when missing the aname query parameter. """
|
||||
act.return_value = self.FakeProxyResponse()
|
||||
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id})
|
||||
url = reverse('proxy_legacy_analytics', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {})
|
||||
print response.content
|
||||
self.assertEqual(response.status_code, 400)
|
||||
self.assertFalse(act.called)
|
||||
|
||||
@@ -1917,31 +1948,15 @@ class TestInstructorAPIHelpers(TestCase):
|
||||
self.assertEqual(_split_input_list(scary_unistuff), [scary_unistuff])
|
||||
|
||||
def test_msk_from_problem_urlname(self):
|
||||
course_id = 'RobotU/Robots101/3001_Spring'
|
||||
capa_urlname = 'capa_urlname'
|
||||
capa_urlname_xml = 'capa_urlname.xml'
|
||||
xblock_urlname = 'notaproblem/someothername'
|
||||
xblock_urlname_xml = 'notaproblem/someothername.xml'
|
||||
|
||||
capa_msk = 'i4x://RobotU/Robots101/problem/capa_urlname'
|
||||
xblock_msk = 'i4x://RobotU/Robots101/notaproblem/someothername'
|
||||
|
||||
for urlname in [capa_urlname, capa_urlname_xml]:
|
||||
self.assertEqual(
|
||||
_msk_from_problem_urlname(course_id, urlname),
|
||||
capa_msk
|
||||
)
|
||||
|
||||
for urlname in [xblock_urlname, xblock_urlname_xml]:
|
||||
self.assertEqual(
|
||||
_msk_from_problem_urlname(course_id, urlname),
|
||||
xblock_msk
|
||||
)
|
||||
course_id = SlashSeparatedCourseKey('MITx', '6.002x', '2013_Spring')
|
||||
name = 'L2Node1'
|
||||
output = 'i4x://MITx/6.002x/problem/L2Node1'
|
||||
self.assertEqual(msk_from_problem_urlname(course_id, name).to_deprecated_string(), output)
|
||||
|
||||
@raises(ValueError)
|
||||
def test_msk_from_problem_urlname_error(self):
|
||||
args = ('notagoodcourse', 'L2Node1')
|
||||
_msk_from_problem_urlname(*args)
|
||||
msk_from_problem_urlname(*args)
|
||||
|
||||
|
||||
@override_settings(MODULESTORE=TEST_DATA_MIXED_MODULESTORE)
|
||||
@@ -1959,60 +1974,60 @@ class TestDueDateExtensions(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
week1 = ItemFactory.create(due=due)
|
||||
week2 = ItemFactory.create(due=due)
|
||||
week3 = ItemFactory.create(due=due)
|
||||
course.children = [week1.location.url(), week2.location.url(),
|
||||
week3.location.url()]
|
||||
course.children = [week1.location.to_deprecated_string(), week2.location.to_deprecated_string(),
|
||||
week3.location.to_deprecated_string()]
|
||||
|
||||
homework = ItemFactory.create(
|
||||
parent_location=week1.location,
|
||||
due=due
|
||||
)
|
||||
week1.children = [homework.location.url()]
|
||||
week1.children = [homework.location.to_deprecated_string()]
|
||||
|
||||
user1 = UserFactory.create()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user1.id,
|
||||
course_id=course.id,
|
||||
module_state_key=week1.location.url()).save()
|
||||
module_id=week1.location).save()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user1.id,
|
||||
course_id=course.id,
|
||||
module_state_key=week2.location.url()).save()
|
||||
module_id=week2.location).save()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user1.id,
|
||||
course_id=course.id,
|
||||
module_state_key=week3.location.url()).save()
|
||||
module_id=week3.location).save()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user1.id,
|
||||
course_id=course.id,
|
||||
module_state_key=homework.location.url()).save()
|
||||
module_id=homework.location).save()
|
||||
|
||||
user2 = UserFactory.create()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user2.id,
|
||||
course_id=course.id,
|
||||
module_state_key=week1.location.url()).save()
|
||||
module_id=week1.location).save()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user2.id,
|
||||
course_id=course.id,
|
||||
module_state_key=homework.location.url()).save()
|
||||
module_id=homework.location).save()
|
||||
|
||||
user3 = UserFactory.create()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user3.id,
|
||||
course_id=course.id,
|
||||
module_state_key=week1.location.url()).save()
|
||||
module_id=week1.location).save()
|
||||
StudentModule(
|
||||
state='{}',
|
||||
student_id=user3.id,
|
||||
course_id=course.id,
|
||||
module_state_key=homework.location.url()).save()
|
||||
module_id=homework.location).save()
|
||||
|
||||
self.course = course
|
||||
self.week1 = week1
|
||||
@@ -2021,14 +2036,14 @@ class TestDueDateExtensions(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
self.user1 = user1
|
||||
self.user2 = user2
|
||||
|
||||
self.instructor = InstructorFactory(course=course.location)
|
||||
self.instructor = InstructorFactory(course=course.id)
|
||||
self.client.login(username=self.instructor.username, password='test')
|
||||
|
||||
def test_change_due_date(self):
|
||||
url = reverse('change_due_date', kwargs={'course_id': self.course.id})
|
||||
url = reverse('change_due_date', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'student': self.user1.username,
|
||||
'url': self.week1.location.url(),
|
||||
'url': self.week1.location.to_deprecated_string(),
|
||||
'due_datetime': '12/30/2013 00:00'
|
||||
})
|
||||
self.assertEqual(response.status_code, 200, response.content)
|
||||
@@ -2037,10 +2052,10 @@ class TestDueDateExtensions(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
|
||||
def test_reset_date(self):
|
||||
self.test_change_due_date()
|
||||
url = reverse('reset_due_date', kwargs={'course_id': self.course.id})
|
||||
url = reverse('reset_due_date', kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {
|
||||
'student': self.user1.username,
|
||||
'url': self.week1.location.url(),
|
||||
'url': self.week1.location.to_deprecated_string(),
|
||||
})
|
||||
self.assertEqual(response.status_code, 200, response.content)
|
||||
self.assertEqual(None,
|
||||
@@ -2049,8 +2064,8 @@ class TestDueDateExtensions(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_show_unit_extensions(self):
|
||||
self.test_change_due_date()
|
||||
url = reverse('show_unit_extensions',
|
||||
kwargs={'course_id': self.course.id})
|
||||
response = self.client.get(url, {'url': self.week1.location.url()})
|
||||
kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'url': self.week1.location.to_deprecated_string()})
|
||||
self.assertEqual(response.status_code, 200, response.content)
|
||||
self.assertEqual(json.loads(response.content), {
|
||||
u'data': [{u'Extended Due Date': u'2013-12-30 00:00',
|
||||
@@ -2063,7 +2078,7 @@ class TestDueDateExtensions(ModuleStoreTestCase, LoginEnrollmentTestCase):
|
||||
def test_show_student_extensions(self):
|
||||
self.test_change_due_date()
|
||||
url = reverse('show_student_extensions',
|
||||
kwargs={'course_id': self.course.id})
|
||||
kwargs={'course_id': self.course.id.to_deprecated_string()})
|
||||
response = self.client.get(url, {'student': self.user1.username})
|
||||
self.assertEqual(response.status_code, 200, response.content)
|
||||
self.assertEqual(json.loads(response.content), {
|
||||
|
||||
Reference in New Issue
Block a user