From 74ef4664c5edc72ce05eb2dc5db5b998378c3be1 Mon Sep 17 00:00:00 2001 From: David Ormsbee Date: Wed, 10 Mar 2021 22:24:35 -0500 Subject: [PATCH] fix: Use fallback when titles are unavailable for outlines. The Studio UI prevents you from creating a Section or Subsection with no title (display_name). But OLX import allows you to bypass these checks and create Sections ("chapter" tag) and Subsections ("sequential" tag) without display_name information specified in the XML. When this happens, Studio and the LMS fall back to using the url_name (the last part of the UsageKey) as a title, using the display_name_with_default method. This usually works, because url_names are derived from the import file name, and if you're hand-editing a course in XML, your file names are probably more intelligible than Mongo object IDs. In any case, this commit updates get_outline_from_modulestore to match the behavior of Studio and the LMS with respect to this situation. This is part of the course outlines backfill rollout. TNL-8056 --- cms/djangoapps/contentstore/outlines.py | 6 +++--- .../contentstore/tests/test_outlines.py | 20 +++++++++++++++++++ 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/cms/djangoapps/contentstore/outlines.py b/cms/djangoapps/contentstore/outlines.py index 708afdf98c..7bb963ec6e 100644 --- a/cms/djangoapps/contentstore/outlines.py +++ b/cms/djangoapps/contentstore/outlines.py @@ -123,7 +123,7 @@ def _make_section_data(section): sequences_data.append( CourseLearningSequenceData( usage_key=_remove_version_info(sequence.location), - title=sequence.display_name, + title=sequence.display_name_with_default, inaccessible_after_due=sequence.hide_after_due, exam=ExamData( is_practice_exam=sequence.is_practice_exam, @@ -139,7 +139,7 @@ def _make_section_data(section): section_data = CourseSectionData( usage_key=_remove_version_info(section.location), - title=section.display_name, + title=section.display_name_with_default, sequences=sequences_data, visibility=VisibilityData( hide_from_toc=section.hide_from_toc, @@ -165,7 +165,7 @@ def get_outline_from_modulestore(course_key): course_outline_data = CourseOutlineData( course_key=course_key, - title=course.display_name, + title=course.display_name_with_default, # subtree_edited_on has a tzinfo of bson.tz_util.FixedOffset (which # maps to UTC), but for consistency, we're going to use the standard diff --git a/cms/djangoapps/contentstore/tests/test_outlines.py b/cms/djangoapps/contentstore/tests/test_outlines.py index 12f495cc1e..4454182ea0 100644 --- a/cms/djangoapps/contentstore/tests/test_outlines.py +++ b/cms/djangoapps/contentstore/tests/test_outlines.py @@ -209,6 +209,26 @@ class OutlineFromModuleStoreTestCase(ModuleStoreTestCase): with self.assertRaises(CourseStructureError): get_outline_from_modulestore(self.course_key) + def test_missing_display_names(self): + """ + When display_names are empty, it should fallback on url_names. + """ + with self.store.bulk_operations(self.course_key): + section = ItemFactory.create( + parent_location=self.draft_course.location, + category='chapter', + display_name=None, + ) + sequence = ItemFactory.create( + parent_location=section.location, + category='sequential', + display_name=None, + ) + + outline = get_outline_from_modulestore(self.course_key) + assert outline.sections[0].title == section.url_name + assert outline.sections[0].sequences[0].title == sequence.url_name + def _outline_seq_data(self, modulestore_seq): """ (CourseLearningSequenceData, UsageKey) for a Modulestore sequence.