From 14fc8b57ab136c719ff1c29943f7c242491da558 Mon Sep 17 00:00:00 2001 From: Nicholas D'Alfonso Date: Tue, 21 Jul 2020 17:11:46 -0400 Subject: [PATCH] AA-123 welcome message --- .../course_home_api/outline/v1/serializers.py | 1 + .../outline/v1/tests/test_views.py | 25 +++++++++++ .../course_home_api/outline/v1/views.py | 45 ++++++++++++++++++- lms/djangoapps/course_home_api/urls.py | 10 ++++- 4 files changed, 79 insertions(+), 2 deletions(-) diff --git a/lms/djangoapps/course_home_api/outline/v1/serializers.py b/lms/djangoapps/course_home_api/outline/v1/serializers.py index 59e7893d2c..2448bb8502 100644 --- a/lms/djangoapps/course_home_api/outline/v1/serializers.py +++ b/lms/djangoapps/course_home_api/outline/v1/serializers.py @@ -62,3 +62,4 @@ class OutlineTabSerializer(serializers.Serializer): course_tools = CourseToolSerializer(many=True) dates_widget = DatesWidgetSerializer() handouts_html = serializers.CharField() + welcome_message_html = serializers.CharField() diff --git a/lms/djangoapps/course_home_api/outline/v1/tests/test_views.py b/lms/djangoapps/course_home_api/outline/v1/tests/test_views.py index c4b97484f5..7229dc84ab 100644 --- a/lms/djangoapps/course_home_api/outline/v1/tests/test_views.py +++ b/lms/djangoapps/course_home_api/outline/v1/tests/test_views.py @@ -8,6 +8,7 @@ from django.urls import reverse from course_modes.models import CourseMode from lms.djangoapps.course_home_api.tests.utils import BaseCourseHomeTests from openedx.core.djangoapps.user_api.preferences.api import set_user_preference +from openedx.core.djangoapps.user_api.tests.factories import UserCourseTagFactory from openedx.features.course_experience import COURSE_ENABLE_UNENROLLED_ACCESS_FLAG from student.models import CourseEnrollment from student.tests.factories import UserFactory @@ -97,3 +98,27 @@ class OutlineTabTestViews(BaseCourseHomeTests): self.assertEqual(handouts_html, '

Hi

' if handouts_visible else '') # TODO: write test_get_unknown_course when more data is pulled into the Outline Tab API + + @ddt.data(True, False) + def test_welcome_message(self, welcome_message_is_dismissed): + self.store.create_item( + self.user.id, self.course.id, + 'course_info', + 'updates', + fields={ + 'items': [{ + 'content': '

Welcome

', + 'status': 'visible', + 'date': 'July 23, 2020', + 'id': 1 + }] + } + ) + UserCourseTagFactory( + user=self.user, + course_id=self.course.id, + key='view-welcome-message', + value=False if welcome_message_is_dismissed else True + ) + welcome_message_html = self.client.get(self.url).data['welcome_message_html'] + self.assertEqual(welcome_message_html, None if welcome_message_is_dismissed else '

Welcome

') diff --git a/lms/djangoapps/course_home_api/outline/v1/views.py b/lms/djangoapps/course_home_api/outline/v1/views.py index fe0d9042ae..3f4ae49c59 100644 --- a/lms/djangoapps/course_home_api/outline/v1/views.py +++ b/lms/djangoapps/course_home_api/outline/v1/views.py @@ -2,11 +2,15 @@ Outline Tab Views """ +from rest_framework.decorators import api_view, authentication_classes, permission_classes +from rest_framework.exceptions import APIException, ParseError from rest_framework.generics import RetrieveAPIView from rest_framework.permissions import IsAuthenticated from rest_framework.response import Response +from django.utils.translation import ugettext as _ from edx_django_utils import monitoring as monitoring_utils +from edx_rest_framework_extensions.auth.jwt.authentication import JwtAuthentication from django.urls import reverse from opaque_keys.edx.keys import CourseKey @@ -21,13 +25,22 @@ from lms.djangoapps.courseware.courses import get_course_date_blocks, get_course from lms.djangoapps.courseware.date_summary import TodaysDate from lms.djangoapps.courseware.masquerade import setup_masquerade from openedx.core.djangoapps.content.block_structure.transformers import BlockStructureTransformers +from openedx.core.djangoapps.user_api.course_tag.api import get_course_tag, set_course_tag +from openedx.features.course_experience import COURSE_ENABLE_UNENROLLED_ACCESS_FLAG, LATEST_UPDATE_FLAG from openedx.features.course_experience.course_tools import CourseToolsPluginManager -from openedx.features.course_experience import COURSE_ENABLE_UNENROLLED_ACCESS_FLAG +from openedx.features.course_experience.views.latest_update import LatestUpdateFragmentView +from openedx.features.course_experience.views.welcome_message import PREFERENCE_KEY, WelcomeMessageFragmentView from student.models import CourseEnrollment from xmodule.course_module import COURSE_VISIBILITY_PUBLIC from xmodule.modulestore.django import modulestore +class UnableToDismissWelcomeMessage(APIException): + status_code = 400 + default_detail = 'Unable to dismiss welcome message.' + default_code = 'unable_to_dismiss_welcome_message' + + class OutlineTabView(RetrieveAPIView): """ **Use Cases** @@ -99,6 +112,13 @@ class OutlineTabView(RetrieveAPIView): show_handouts = is_enrolled or is_staff or allow_public handouts_html = get_course_info_section(request, request.user, course, 'handouts') if show_handouts else '' + welcome_message_html = None + if get_course_tag(request.user, course_key, PREFERENCE_KEY) != 'False': + if LATEST_UPDATE_FLAG.is_enabled(course_key): + welcome_message_html = LatestUpdateFragmentView().latest_update_html(request, course) + else: + welcome_message_html = WelcomeMessageFragmentView().welcome_message_html(request, course) + course_tools = CourseToolsPluginManager.get_enabled_course_tools(request, course_key) date_blocks = get_course_date_blocks(course, request.user, request, num_assignments=1) @@ -129,9 +149,32 @@ class OutlineTabView(RetrieveAPIView): 'course_tools': course_tools, 'dates_widget': dates_widget, 'handouts_html': handouts_html, + 'welcome_message_html': welcome_message_html, } context = self.get_serializer_context() context['course_key'] = course_key serializer = self.get_serializer_class()(data, context=context) return Response(serializer.data) + + +@api_view(['POST']) +@authentication_classes((JwtAuthentication,)) +@permission_classes((IsAuthenticated,)) +def dismiss_welcome_message(request): + course_id = request.data.get('course_id', None) + + # If body doesnt contain 'course_id', return 400 to client. + if not course_id: + raise ParseError(_("'course_id' is required.")) + + # If body contains params other than 'course_id', return 400 to client. + if len(request.data) > 1: + raise ParseError(_("Only 'course_id' is expected.")) + + try: + course_key = CourseKey.from_string(course_id) + set_course_tag(request.user, course_key, PREFERENCE_KEY, 'False') + return Response({'message': _('Welcome message successfully dismissed.')}) + except Exception: + raise UnableToDismissWelcomeMessage diff --git a/lms/djangoapps/course_home_api/urls.py b/lms/djangoapps/course_home_api/urls.py index 3a2c3c0771..371e17e8ec 100644 --- a/lms/djangoapps/course_home_api/urls.py +++ b/lms/djangoapps/course_home_api/urls.py @@ -8,7 +8,7 @@ from django.urls import re_path from lms.djangoapps.course_home_api.dates.v1.views import DatesTabView from lms.djangoapps.course_home_api.course_metadata.v1.views import CourseHomeMetadataView -from lms.djangoapps.course_home_api.outline.v1.views import OutlineTabView +from lms.djangoapps.course_home_api.outline.v1.views import OutlineTabView, dismiss_welcome_message from lms.djangoapps.course_home_api.progress.v1.views import ProgressTabView urlpatterns = [] @@ -40,6 +40,14 @@ urlpatterns += [ ), ] +urlpatterns += [ + re_path( + r'v1/dismiss_welcome_message', + dismiss_welcome_message, + name='course-experience-dismiss-welcome-message' + ), +] + # Progress Tab URLs urlpatterns += [ re_path(