diff --git a/common/test/data/open_ended_nopath/README.md b/common/test/data/open_ended_nopath/README.md new file mode 100644 index 0000000000..1e57b483bc --- /dev/null +++ b/common/test/data/open_ended_nopath/README.md @@ -0,0 +1 @@ +This is a very very simple course, useful for debugging open ended grading code. This is specifically for testing if a peer grading module with no path to it in the course will be handled properly. diff --git a/common/test/data/open_ended_nopath/course.xml b/common/test/data/open_ended_nopath/course.xml new file mode 100644 index 0000000000..d60df1a471 --- /dev/null +++ b/common/test/data/open_ended_nopath/course.xml @@ -0,0 +1 @@ + diff --git a/common/test/data/open_ended_nopath/course/2012_Fall.xml b/common/test/data/open_ended_nopath/course/2012_Fall.xml new file mode 100644 index 0000000000..2535b4f462 --- /dev/null +++ b/common/test/data/open_ended_nopath/course/2012_Fall.xml @@ -0,0 +1,4 @@ + + + + diff --git a/common/test/data/open_ended_nopath/peergrading/PeerGradingNoPath.xml b/common/test/data/open_ended_nopath/peergrading/PeerGradingNoPath.xml new file mode 100644 index 0000000000..7e3afddf3a --- /dev/null +++ b/common/test/data/open_ended_nopath/peergrading/PeerGradingNoPath.xml @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/common/test/data/open_ended_nopath/policies/2012_Fall.json b/common/test/data/open_ended_nopath/policies/2012_Fall.json new file mode 100644 index 0000000000..321cdf21df --- /dev/null +++ b/common/test/data/open_ended_nopath/policies/2012_Fall.json @@ -0,0 +1,11 @@ +{ + "course/2012_Fall": { + "graceperiod": "2 days 5 hours 59 minutes 59 seconds", + "start": "2015-07-17T12:00", + "display_name": "Self Assessment Test", + "graded": "true" + }, + "chapter/Overview": { + "display_name": "Overview" + } +} diff --git a/lms/djangoapps/courseware/tests/modulestore_config.py b/lms/djangoapps/courseware/tests/modulestore_config.py index 74fd3da57f..681f3fd4d1 100644 --- a/lms/djangoapps/courseware/tests/modulestore_config.py +++ b/lms/djangoapps/courseware/tests/modulestore_config.py @@ -22,5 +22,6 @@ MAPPINGS = { 'edX/test_about_blob_end_date/2012_Fall': 'xml', 'edX/graded/2012_Fall': 'xml', 'edX/open_ended/2012_Fall': 'xml', + 'edX/open_ended_nopath/2012_Fall': 'xml', } TEST_DATA_MIXED_MODULESTORE = mixed_store_config(TEST_DATA_DIR, MAPPINGS) diff --git a/lms/djangoapps/open_ended_grading/tests.py b/lms/djangoapps/open_ended_grading/tests.py index 27e6fd6059..7ea81f4f3f 100644 --- a/lms/djangoapps/open_ended_grading/tests.py +++ b/lms/djangoapps/open_ended_grading/tests.py @@ -320,3 +320,22 @@ class TestPanel(ModuleStoreTestCase, LoginEnrollmentTestCase): request = Mock(user=self.user) response = views.student_problem_list(request, self.course.id) self.assertRegexpMatches(response.content, "Here are a list of open ended problems for this course.") + +@override_settings(MODULESTORE=TEST_DATA_MIXED_MODULESTORE) +class TestPeerGradingFound(ModuleStoreTestCase): + """ + Test to see if peer grading modules can be found properly. + """ + + def setUp(self): + self.course_name = 'edX/open_ended_nopath/2012_Fall' + self.course = modulestore().get_course(self.course_name) + + def test_peer_grading_nopath(self): + """ + The open_ended_nopath course contains a peer grading module with no path to it. + Ensure that the exception is caught. + """ + + found, url = views.find_peer_grading_module(self.course) + self.assertEqual(found, False) \ No newline at end of file diff --git a/lms/djangoapps/open_ended_grading/views.py b/lms/djangoapps/open_ended_grading/views.py index e060f4c131..f5a2471226 100644 --- a/lms/djangoapps/open_ended_grading/views.py +++ b/lms/djangoapps/open_ended_grading/views.py @@ -97,28 +97,31 @@ def find_peer_grading_module(course): @param course: A course object. @return: boolean found_module, string problem_url """ - #Reverse the base course url + + # Reverse the base course url. base_course_url = reverse('courses') found_module = False problem_url = "" - #Get the course id and split it + # Get the course id and split it. course_id_parts = course.id.split("/") log.info("COURSE ID PARTS") log.info(course_id_parts) - #Get the peer grading modules currently in the course. Explicitly specify the course id to avoid issues with different runs. + # Get the peer grading modules currently in the course. Explicitly specify the course id to avoid issues with different runs. items = modulestore().get_items(['i4x', course_id_parts[0], course_id_parts[1], 'peergrading', None], course_id=course.id) #See if any of the modules are centralized modules (ie display info from multiple problems) items = [i for i in items if not getattr(i, "use_for_single_location", True)] - #Get the first one + # Loop through all potential peer grading modules, and find the first one that has a path to it. for item in items: item_location = item.location - #Generate a url for the first module and redirect the user to it + # Generate a url for the first module and redirect the user to it. try: problem_url_parts = search.path_to_location(modulestore(), course.id, item_location) except NoPathToItem: - log.info("Invalid peer grading module location {0} in course {1}.".format(item_location, course.id)) + # In the case of nopathtoitem, the peer grading module that was found is in an invalid state, and + # can no longer be accessed. Log an informational message, but this will not impact normal behavior. + log.info("Invalid peer grading module location {0} in course {1}. This module may need to be removed.".format(item_location, course.id)) continue problem_url = generate_problem_url(problem_url_parts, base_course_url) found_module = True