Merge branch 'master' into hamza/ENT-9440-samlproviderconfig-history-tracking
This commit is contained in:
@@ -31,4 +31,3 @@ class CourseSettingsSerializer(serializers.Serializer):
|
||||
show_min_grade_warning = serializers.BooleanField()
|
||||
sidebar_html_enabled = serializers.BooleanField()
|
||||
upgrade_deadline = serializers.DateTimeField(allow_null=True)
|
||||
use_v2_cert_display_settings = serializers.BooleanField()
|
||||
|
||||
@@ -95,7 +95,6 @@ class CourseSettingsView(DeveloperErrorViewMixin, APIView):
|
||||
"show_min_grade_warning": false,
|
||||
"sidebar_html_enabled": true,
|
||||
"upgrade_deadline": null,
|
||||
"use_v2_cert_display_settings": false
|
||||
}
|
||||
```
|
||||
"""
|
||||
@@ -112,7 +111,6 @@ class CourseSettingsView(DeveloperErrorViewMixin, APIView):
|
||||
'course_display_name_with_default': course_block.display_name_with_default,
|
||||
'platform_name': settings.PLATFORM_NAME,
|
||||
'licensing_enabled': settings.FEATURES.get("LICENSING", False),
|
||||
'use_v2_cert_display_settings': settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS", False),
|
||||
})
|
||||
|
||||
serializer = CourseSettingsSerializer(settings_context)
|
||||
|
||||
@@ -55,7 +55,6 @@ class CourseSettingsViewTest(CourseTestCase, PermissionAccessMixin):
|
||||
"show_min_grade_warning": False,
|
||||
"upgrade_deadline": None,
|
||||
"licensing_enabled": False,
|
||||
"use_v2_cert_display_settings": False,
|
||||
}
|
||||
|
||||
self.assertEqual(response.status_code, status.HTTP_200_OK)
|
||||
|
||||
@@ -468,17 +468,6 @@ FEATURES = {
|
||||
# .. toggle_tickets: https://github.com/openedx/edx-platform/pull/26106
|
||||
'ENABLE_HELP_LINK': True,
|
||||
|
||||
# .. toggle_name: FEATURES['ENABLE_V2_CERT_DISPLAY_SETTINGS']
|
||||
# .. toggle_implementation: DjangoSetting
|
||||
# .. toggle_default: False
|
||||
# .. toggle_description: Whether to use the reimagined certificates_display_behavior and certificate_available_date
|
||||
# .. settings. Will eventually become the default.
|
||||
# .. toggle_use_cases: temporary
|
||||
# .. toggle_creation_date: 2021-07-26
|
||||
# .. toggle_target_removal_date: 2021-10-01
|
||||
# .. toggle_tickets: 'https://openedx.atlassian.net/browse/MICROBA-1405'
|
||||
'ENABLE_V2_CERT_DISPLAY_SETTINGS': False,
|
||||
|
||||
# .. toggle_name: FEATURES['ENABLE_INTEGRITY_SIGNATURE']
|
||||
# .. toggle_implementation: DjangoSetting
|
||||
# .. toggle_default: False
|
||||
|
||||
@@ -43,7 +43,6 @@ CMS.URL.UPLOAD_ASSET = '${upload_asset_url | n, js_escaped_string}'
|
||||
${show_min_grade_warning | n, dump_js_escaped_json},
|
||||
${can_show_certificate_available_date_field(context_course) | n, dump_js_escaped_json},
|
||||
"${upgrade_deadline | n, js_escaped_string}",
|
||||
${settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS") | n, dump_js_escaped_json}
|
||||
);
|
||||
});
|
||||
</%block>
|
||||
@@ -251,58 +250,45 @@ CMS.URL.UPLOAD_ASSET = '${upload_asset_url | n, js_escaped_string}'
|
||||
</li>
|
||||
</ol>
|
||||
|
||||
<%
|
||||
use_v2_cert_display_settings = settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS", False)
|
||||
%>
|
||||
% if can_show_certificate_available_date_field(context_course):
|
||||
<ol class="list-input">
|
||||
<li class="field-group field-group-certificate-available" id="certificate-available">
|
||||
<div class="field date" id="field-certificates-display-behavior">
|
||||
<label for="certificates-display-behavior">${_("Certificates Display Behavior")}</label>
|
||||
% if use_v2_cert_display_settings:
|
||||
<select id="certificates-display-behavior">
|
||||
<option value="early_no_info">${_("Immediately upon passing")}</option>
|
||||
<option value="end">${_("End date of course")}</option>
|
||||
<option value="end_with_date">${_("A date after the course end date")}</option>
|
||||
</select>
|
||||
% else:
|
||||
<input id="certificates-display-behavior" type="text">
|
||||
% endif
|
||||
<select id="certificates-display-behavior">
|
||||
<option value="early_no_info">${_("Immediately upon passing")}</option>
|
||||
<option value="end">${_("End date of course")}</option>
|
||||
<option value="end_with_date">${_("A date after the course end date")}</option>
|
||||
</select>
|
||||
<span class="tip tip-stacked">${_("Certificates are awarded at the end of a course run")}</span>
|
||||
|
||||
% if use_v2_cert_display_settings:
|
||||
<!-- Collapsible -->
|
||||
<div class="collapsible">
|
||||
<div id="certificate-display-behavior-collapsible-trigger" class="collapsible-trigger" role="button" tabindex="0" aria-expanded="false">
|
||||
<span>
|
||||
<span class="icon icon-inline fa fa-info-circle" aria-hidden="true"></span>
|
||||
${_("Read more about this setting")}
|
||||
</span>
|
||||
<!-- Collapsible -->
|
||||
<div class="collapsible">
|
||||
<div id="certificate-display-behavior-collapsible-trigger" class="collapsible-trigger" role="button" tabindex="0" aria-expanded="false">
|
||||
<span>
|
||||
<span class="icon icon-inline fa fa-info-circle" aria-hidden="true"></span>
|
||||
${_("Read more about this setting")}
|
||||
</span>
|
||||
</div>
|
||||
<div id="certificate-display-behavior-collapsible-content" class="collapsible-content collapsed">
|
||||
<p>${_("In all configurations of this setting, certificates are generated for learners as soon as they achieve the passing threshold in the course (which can occur before a final assignment based on course design)")}</p>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("Immediately upon passing")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners can access their certificate as soon as they achieve a passing grade above the course grade threshold. Note: learners can achieve a passing grade before encountering all assignments in some course configurations.")}</div>
|
||||
</div>
|
||||
<div id="certificate-display-behavior-collapsible-content" class="collapsible-content collapsed">
|
||||
<p>${_("In all configurations of this setting, certificates are generated for learners as soon as they achieve the passing threshold in the course (which can occur before a final assignment based on course design)")}</p>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("Immediately upon passing")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners can access their certificate as soon as they achieve a passing grade above the course grade threshold. Note: learners can achieve a passing grade before encountering all assignments in some course configurations.")}</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("On course end date")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners with passing grades can access their certificate once the end date of the course has elapsed.")}</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("A date after the course end date")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners with passing grades can access their certificate after the date that you set has elapsed.")}</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("On course end date")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners with passing grades can access their certificate once the end date of the course has elapsed.")}</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="collapsible-description-heading">${_("A date after the course end date")}</div>
|
||||
<div class="collapsible-description-description">${_("Learners with passing grades can access their certificate after the date that you set has elapsed.")}</div>
|
||||
</div>
|
||||
</div>
|
||||
% endif
|
||||
</div>
|
||||
</div>
|
||||
|
||||
% if use_v2_cert_display_settings:
|
||||
<div class="field date hidden" id="field-certificate-available-date" >
|
||||
% else:
|
||||
<div class="field date" id="field-certificate-available-date" >
|
||||
% endif
|
||||
<div class="field date hidden" id="field-certificate-available-date" >
|
||||
<label for="certificate-available-date">${_("Certificates Available Date")}</label>
|
||||
<input type="text" class="certificate-available-date date start datepicker" id="certificate-available-date" placeholder="MM/DD/YYYY" autocomplete="off" />
|
||||
<span class="icon icon-inline fa fa-calendar-check-o datepicker-icon" aria-hidden="true"></span>
|
||||
|
||||
@@ -646,21 +646,14 @@ def _is_certificate_earned_but_not_available(course_overview, status):
|
||||
(bool): True if the user earned the certificate but it's hidden due to display behavior, else False
|
||||
|
||||
"""
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
return (
|
||||
not certificates_viewable_for_course(course_overview)
|
||||
and CertificateStatuses.is_passing_status(status)
|
||||
and course_overview.certificates_display_behavior in (
|
||||
CertificatesDisplayBehaviors.END_WITH_DATE,
|
||||
CertificatesDisplayBehaviors.END
|
||||
)
|
||||
)
|
||||
else:
|
||||
return (
|
||||
not certificates_viewable_for_course(course_overview) and
|
||||
CertificateStatuses.is_passing_status(status) and
|
||||
course_overview.certificate_available_date
|
||||
return (
|
||||
not certificates_viewable_for_course(course_overview)
|
||||
and CertificateStatuses.is_passing_status(status)
|
||||
and course_overview.certificates_display_behavior in (
|
||||
CertificatesDisplayBehaviors.END_WITH_DATE,
|
||||
CertificatesDisplayBehaviors.END
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
def process_survey_link(survey_link, user):
|
||||
|
||||
@@ -10,7 +10,6 @@ certificates models or any other certificates modules.
|
||||
import logging
|
||||
from datetime import datetime
|
||||
|
||||
from django.conf import settings
|
||||
from django.contrib.auth import get_user_model
|
||||
from django.core.exceptions import ObjectDoesNotExist
|
||||
from django.db.models import Q
|
||||
@@ -286,12 +285,9 @@ def certificate_downloadable_status(student, course_key):
|
||||
|
||||
course_overview = get_course_overview_or_none(course_key)
|
||||
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
display_behavior_is_valid = (
|
||||
course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
)
|
||||
else:
|
||||
display_behavior_is_valid = True
|
||||
display_behavior_is_valid = (
|
||||
course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
)
|
||||
|
||||
if (
|
||||
not certificates_viewable_for_course(course_overview)
|
||||
@@ -837,10 +833,7 @@ def can_show_certificate_message(course, student, course_grade, certificates_ena
|
||||
|
||||
def _course_uses_available_date(course):
|
||||
"""Returns if the course has an certificate_available_date set and that it should be used"""
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
display_behavior_is_valid = course.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
else:
|
||||
display_behavior_is_valid = True
|
||||
display_behavior_is_valid = course.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
|
||||
return (
|
||||
can_show_certificate_available_date_field(course)
|
||||
|
||||
@@ -209,29 +209,6 @@ class CertificateDownloadableStatusTests(WebCertificateTestMixin, ModuleStoreTes
|
||||
"uuid": cert_status["uuid"],
|
||||
}
|
||||
|
||||
@ddt.data(
|
||||
(False, timedelta(days=2), False, True),
|
||||
(False, -timedelta(days=2), True, None),
|
||||
(True, timedelta(days=2), True, None),
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, {"CERTIFICATES_HTML_VIEW": True})
|
||||
@patch.dict(settings.FEATURES, {"ENABLE_V2_CERT_DISPLAY_SETTINGS": False})
|
||||
def test_cert_api_return_v1(self, self_paced, cert_avail_delta, cert_downloadable_status, earned_but_not_available):
|
||||
"""
|
||||
Test 'downloadable status'
|
||||
"""
|
||||
cert_avail_date = datetime.now(pytz.UTC) + cert_avail_delta
|
||||
self.course.self_paced = self_paced
|
||||
self.course.certificate_available_date = cert_avail_date
|
||||
self.course.save()
|
||||
|
||||
self._setup_course_certificate()
|
||||
|
||||
downloadable_status = certificate_downloadable_status(self.student, self.course.id)
|
||||
assert downloadable_status["is_downloadable"] == cert_downloadable_status
|
||||
assert downloadable_status.get("earned_but_not_available") == earned_but_not_available
|
||||
|
||||
@ddt.data(
|
||||
(True, timedelta(days=2), CertificatesDisplayBehaviors.END_WITH_DATE, True, None),
|
||||
(False, -timedelta(days=2), CertificatesDisplayBehaviors.EARLY_NO_INFO, True, None),
|
||||
@@ -243,8 +220,7 @@ class CertificateDownloadableStatusTests(WebCertificateTestMixin, ModuleStoreTes
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, {"CERTIFICATES_HTML_VIEW": True})
|
||||
@patch.dict(settings.FEATURES, {"ENABLE_V2_CERT_DISPLAY_SETTINGS": True})
|
||||
def test_cert_api_return_v2(
|
||||
def test_cert_api_return(
|
||||
self,
|
||||
self_paced,
|
||||
cert_avail_delta,
|
||||
|
||||
@@ -5,7 +5,6 @@ from datetime import datetime, timedelta
|
||||
from unittest.mock import patch
|
||||
|
||||
import ddt
|
||||
from django.conf import settings
|
||||
from django.test import TestCase
|
||||
from pytz import utc
|
||||
|
||||
@@ -80,40 +79,7 @@ class CertificateUtilityTests(TestCase):
|
||||
(CertificatesDisplayBehaviors.END, False, False, _LAST_MONTH, True, True),
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=True)
|
||||
def test_should_certificate_be_visible_v2(
|
||||
self,
|
||||
certificates_display_behavior,
|
||||
certificates_show_before_end,
|
||||
has_ended,
|
||||
certificate_available_date,
|
||||
self_paced,
|
||||
expected_value
|
||||
):
|
||||
"""Test whether the certificate should be visible to user given multiple usecases"""
|
||||
assert should_certificate_be_visible(
|
||||
certificates_display_behavior,
|
||||
certificates_show_before_end,
|
||||
has_ended,
|
||||
certificate_available_date,
|
||||
self_paced
|
||||
) == expected_value
|
||||
|
||||
@ddt.data(
|
||||
('early_with_info', True, True, _LAST_MONTH, False, True),
|
||||
('early_no_info', False, False, _LAST_MONTH, False, True),
|
||||
('end', True, False, _LAST_MONTH, False, True),
|
||||
('end', False, True, _LAST_MONTH, False, True),
|
||||
('end', False, False, _NEXT_WEEK, False, False),
|
||||
('end', False, False, _LAST_WEEK, False, True),
|
||||
('end', False, False, None, False, False),
|
||||
('early_with_info', False, False, None, False, True),
|
||||
('end', False, False, _NEXT_WEEK, False, False),
|
||||
('end', False, False, _NEXT_WEEK, True, True),
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=False)
|
||||
def test_should_certificate_be_visible_v1(
|
||||
def test_should_certificate_be_visible(
|
||||
self,
|
||||
certificates_display_behavior,
|
||||
certificates_show_before_end,
|
||||
|
||||
@@ -153,30 +153,19 @@ def should_certificate_be_visible(
|
||||
certificate_available_date (datetime): the date the certificate is available on for the course.
|
||||
self_paced (bool): Whether the course is self-paced.
|
||||
"""
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
show_early = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.EARLY_NO_INFO
|
||||
or certificates_show_before_end
|
||||
)
|
||||
past_available_date = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and certificate_available_date
|
||||
and certificate_available_date < datetime.now(utc)
|
||||
)
|
||||
ended_without_available_date = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.END
|
||||
and has_ended
|
||||
)
|
||||
else:
|
||||
show_early = (
|
||||
certificates_display_behavior in ('early_with_info', 'early_no_info')
|
||||
or certificates_show_before_end
|
||||
)
|
||||
past_available_date = (
|
||||
certificate_available_date
|
||||
and certificate_available_date < datetime.now(utc)
|
||||
)
|
||||
ended_without_available_date = (certificate_available_date is None) and has_ended
|
||||
show_early = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.EARLY_NO_INFO
|
||||
or certificates_show_before_end
|
||||
)
|
||||
past_available_date = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and certificate_available_date
|
||||
and certificate_available_date < datetime.now(utc)
|
||||
)
|
||||
ended_without_available_date = (
|
||||
certificates_display_behavior == CertificatesDisplayBehaviors.END
|
||||
and has_ended
|
||||
)
|
||||
|
||||
return any((self_paced, show_early, past_available_date, ended_without_available_date))
|
||||
|
||||
|
||||
@@ -353,28 +353,22 @@ def _get_user_certificate(request, user, course_key, course_overview, preview_mo
|
||||
if preview_mode:
|
||||
# certificate is being previewed from studio
|
||||
if request.user.has_perm(PREVIEW_CERTIFICATES, course_overview):
|
||||
if not settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
if course_overview.certificate_available_date and not course_overview.self_paced:
|
||||
modified_date = course_overview.certificate_available_date
|
||||
else:
|
||||
modified_date = datetime.now().date()
|
||||
if (
|
||||
course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and course_overview.certificate_available_date
|
||||
and not course_overview.self_paced
|
||||
):
|
||||
modified_date = course_overview.certificate_available_date
|
||||
elif course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END:
|
||||
modified_date = course_overview.end
|
||||
else:
|
||||
if (
|
||||
course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and course_overview.certificate_available_date
|
||||
and not course_overview.self_paced
|
||||
):
|
||||
modified_date = course_overview.certificate_available_date
|
||||
elif course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END:
|
||||
modified_date = course_overview.end
|
||||
else:
|
||||
modified_date = datetime.now().date()
|
||||
user_certificate = GeneratedCertificate(
|
||||
mode=preview_mode,
|
||||
verify_uuid=str(uuid4().hex),
|
||||
modified_date=modified_date,
|
||||
created_date=datetime.now().date(),
|
||||
)
|
||||
modified_date = datetime.now().date()
|
||||
user_certificate = GeneratedCertificate(
|
||||
mode=preview_mode,
|
||||
verify_uuid=str(uuid4().hex),
|
||||
modified_date=modified_date,
|
||||
created_date=datetime.now().date(),
|
||||
)
|
||||
elif certificates_viewable_for_course(course_overview):
|
||||
# certificate is being viewed by learner or public
|
||||
try:
|
||||
|
||||
@@ -299,23 +299,20 @@ class CertificateSerializer(serializers.Serializer):
|
||||
def get_availableDate(self, enrollment):
|
||||
"""Available date changes based off of Certificate display behavior"""
|
||||
course_overview = enrollment.course_overview
|
||||
available_date = course_overview.certificate_available_date
|
||||
available_date = None
|
||||
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS", False):
|
||||
if (
|
||||
course_overview.certificates_display_behavior
|
||||
== CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and course_overview.certificate_available_date
|
||||
):
|
||||
available_date = course_overview.certificate_available_date
|
||||
elif (
|
||||
course_overview.certificates_display_behavior
|
||||
== CertificatesDisplayBehaviors.END
|
||||
and course_overview.end
|
||||
):
|
||||
available_date = course_overview.end
|
||||
else:
|
||||
if (
|
||||
course_overview.certificates_display_behavior
|
||||
== CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
and course_overview.certificate_available_date
|
||||
):
|
||||
available_date = course_overview.certificate_available_date
|
||||
elif (
|
||||
course_overview.certificates_display_behavior
|
||||
== CertificatesDisplayBehaviors.END
|
||||
and course_overview.end
|
||||
):
|
||||
available_date = course_overview.end
|
||||
|
||||
return serializers.DateTimeField().to_representation(available_date)
|
||||
|
||||
|
||||
@@ -522,9 +522,12 @@ class TestCertificateSerializer(LearnerDashboardBaseTest):
|
||||
# ... with a certificate
|
||||
input_context = self.create_test_context(input_data.course)
|
||||
|
||||
# ... and some data preemptively gathered
|
||||
# ... and some data preemptively gathered, including a certificate display behavior
|
||||
available_date = random_date()
|
||||
input_data.course.certificate_available_date = available_date
|
||||
input_data.course.certificates_display_behavior = (
|
||||
CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
)
|
||||
cert_url = input_context["cert_statuses"][input_data.course.id][
|
||||
"cert_web_view_url"
|
||||
]
|
||||
@@ -544,23 +547,6 @@ class TestCertificateSerializer(LearnerDashboardBaseTest):
|
||||
},
|
||||
)
|
||||
|
||||
@mock.patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=False)
|
||||
def test_available_date_old_format(self):
|
||||
# Given new cert display settings are not enabled
|
||||
input_data = self.create_test_enrollment(course_mode=CourseMode.VERIFIED)
|
||||
input_data.course.certificate_available_date = random_date()
|
||||
input_context = self.create_test_context(input_data.course)
|
||||
|
||||
# When I get certificate info
|
||||
output_data = CertificateSerializer(input_data, context=input_context).data
|
||||
|
||||
# Then the available date is defaulted to the certificate available date
|
||||
expected_available_date = datetime_to_django_format(
|
||||
input_data.course.certificate_available_date
|
||||
)
|
||||
self.assertEqual(output_data["availableDate"], expected_available_date)
|
||||
|
||||
@mock.patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=True)
|
||||
def test_available_date_course_end(self):
|
||||
# Given new cert display settings are enabled
|
||||
input_data = self.create_test_enrollment(course_mode=CourseMode.VERIFIED)
|
||||
@@ -578,7 +564,6 @@ class TestCertificateSerializer(LearnerDashboardBaseTest):
|
||||
expected_available_date = datetime_to_django_format(input_data.course.end)
|
||||
self.assertEqual(output_data["availableDate"], expected_available_date)
|
||||
|
||||
@mock.patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=True)
|
||||
def test_available_date_specific_end(self):
|
||||
# Given new cert display settings are enabled
|
||||
input_data = self.create_test_enrollment(course_mode=CourseMode.VERIFIED)
|
||||
|
||||
@@ -949,17 +949,6 @@ FEATURES = {
|
||||
# .. toggle_tickets: 'https://openedx.atlassian.net/browse/OSPR-5290'
|
||||
'ENABLE_BULK_USER_RETIREMENT': False,
|
||||
|
||||
# .. toggle_name: FEATURES['ENABLE_V2_CERT_DISPLAY_SETTINGS']
|
||||
# .. toggle_implementation: DjangoSetting
|
||||
# .. toggle_default: False
|
||||
# .. toggle_description: Whether to use the reimagined certificates_display_behavior and certificate_available_date
|
||||
# .. settings. Will eventually become the default.
|
||||
# .. toggle_use_cases: temporary
|
||||
# .. toggle_creation_date: 2021-07-26
|
||||
# .. toggle_target_removal_date: 2021-10-01
|
||||
# .. toggle_tickets: 'https://openedx.atlassian.net/browse/MICROBA-1405'
|
||||
'ENABLE_V2_CERT_DISPLAY_SETTINGS': False,
|
||||
|
||||
# .. toggle_name: FEATURES['ENABLE_INTEGRITY_SIGNATURE']
|
||||
# .. toggle_implementation: DjangoSetting
|
||||
# .. toggle_default: False
|
||||
|
||||
@@ -44,14 +44,11 @@ else:
|
||||
<div class="message message-status ${status_css_class} is-shown">
|
||||
<p class="message-copy">
|
||||
<%
|
||||
if settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS", False):
|
||||
certificate_available_date_string = ""
|
||||
if course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE and course_overview.certificate_available_date:
|
||||
certificate_available_date_string = course_overview.certificate_available_date.strftime('%Y-%m-%dT%H:%M:%S%z')
|
||||
elif course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END and course_overview.end:
|
||||
certificate_available_date_string = course_overview.end.strftime('%Y-%m-%dT%H:%M:%S%z')
|
||||
else:
|
||||
certificate_available_date_string = ""
|
||||
if course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END_WITH_DATE and course_overview.certificate_available_date:
|
||||
certificate_available_date_string = course_overview.certificate_available_date.strftime('%Y-%m-%dT%H:%M:%S%z')
|
||||
elif course_overview.certificates_display_behavior == CertificatesDisplayBehaviors.END and course_overview.end:
|
||||
certificate_available_date_string = course_overview.end.strftime('%Y-%m-%dT%H:%M:%S%z')
|
||||
container_string = _("Your grade and certificate will be ready after {date}.")
|
||||
format = 'shortDate'
|
||||
%>
|
||||
|
||||
@@ -371,10 +371,6 @@ class CourseDetails:
|
||||
tuple[str, str]: updated certificate_available_date, updated certificates_display_behavior
|
||||
None
|
||||
"""
|
||||
# If V2 is not enable, return original values
|
||||
if not settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS", False):
|
||||
return (certificate_available_date, certificates_display_behavior)
|
||||
|
||||
# "early_no_info" will always show regardless of settings
|
||||
if certificates_display_behavior == CertificatesDisplayBehaviors.EARLY_NO_INFO:
|
||||
return (None, CertificatesDisplayBehaviors.EARLY_NO_INFO)
|
||||
|
||||
@@ -8,7 +8,6 @@ from django.test import override_settings
|
||||
import pytest
|
||||
import ddt
|
||||
from pytz import UTC
|
||||
from unittest.mock import patch # lint-amnesty, pylint: disable=wrong-import-order
|
||||
|
||||
from django.conf import settings
|
||||
from xmodule.modulestore import ModuleStoreEnum
|
||||
@@ -212,30 +211,7 @@ class CourseDetailsTestCase(ModuleStoreTestCase):
|
||||
),
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=True)
|
||||
def test_validate_certificate_settings_v2(self, stored_date, stored_behavior, expected_date, expected_behavior):
|
||||
assert CourseDetails.validate_certificate_settings(
|
||||
stored_date, stored_behavior
|
||||
) == (expected_date, expected_behavior)
|
||||
|
||||
@ddt.data(
|
||||
(
|
||||
EXAMPLE_CERTIFICATE_AVAILABLE_DATE,
|
||||
CertificatesDisplayBehaviors.END_WITH_DATE,
|
||||
EXAMPLE_CERTIFICATE_AVAILABLE_DATE,
|
||||
CertificatesDisplayBehaviors.END_WITH_DATE
|
||||
),
|
||||
(
|
||||
None,
|
||||
"invalid_option",
|
||||
None,
|
||||
"invalid_option"
|
||||
),
|
||||
)
|
||||
@ddt.unpack
|
||||
@patch.dict(settings.FEATURES, ENABLE_V2_CERT_DISPLAY_SETTINGS=False)
|
||||
def test_validate_certificate_settings_v1(self, stored_date, stored_behavior, expected_date, expected_behavior):
|
||||
"""Test that method just returns passed in arguments if v2 is off"""
|
||||
def test_validate_certificate_settings(self, stored_date, stored_behavior, expected_date, expected_behavior):
|
||||
assert CourseDetails.validate_certificate_settings(
|
||||
stored_date, stored_behavior
|
||||
) == (expected_date, expected_behavior)
|
||||
|
||||
@@ -26,7 +26,7 @@ celery>=5.2.2,<6.0.0
|
||||
# The team that owns this package will manually bump this package rather than having it pulled in automatically.
|
||||
# This is to allow them to better control its deployment and to do it in a process that works better
|
||||
# for them.
|
||||
edx-enterprise==4.26.0
|
||||
edx-enterprise==4.26.1
|
||||
|
||||
# Stay on LTS version, remove once this is added to common constraint
|
||||
Django<5.0
|
||||
|
||||
@@ -467,7 +467,7 @@ edx-drf-extensions==10.4.0
|
||||
# edx-when
|
||||
# edxval
|
||||
# openedx-learning
|
||||
edx-enterprise==4.26.0
|
||||
edx-enterprise==4.26.1
|
||||
# via
|
||||
# -c requirements/edx/../constraints.txt
|
||||
# -r requirements/edx/kernel.in
|
||||
|
||||
@@ -741,7 +741,7 @@ edx-drf-extensions==10.4.0
|
||||
# edx-when
|
||||
# edxval
|
||||
# openedx-learning
|
||||
edx-enterprise==4.26.0
|
||||
edx-enterprise==4.26.1
|
||||
# via
|
||||
# -c requirements/edx/../constraints.txt
|
||||
# -r requirements/edx/doc.txt
|
||||
|
||||
@@ -547,7 +547,7 @@ edx-drf-extensions==10.4.0
|
||||
# edx-when
|
||||
# edxval
|
||||
# openedx-learning
|
||||
edx-enterprise==4.26.0
|
||||
edx-enterprise==4.26.1
|
||||
# via
|
||||
# -c requirements/edx/../constraints.txt
|
||||
# -r requirements/edx/base.txt
|
||||
|
||||
@@ -571,7 +571,7 @@ edx-drf-extensions==10.4.0
|
||||
# edx-when
|
||||
# edxval
|
||||
# openedx-learning
|
||||
edx-enterprise==4.26.0
|
||||
edx-enterprise==4.26.1
|
||||
# via
|
||||
# -c requirements/edx/../constraints.txt
|
||||
# -r requirements/edx/base.txt
|
||||
|
||||
@@ -1115,9 +1115,6 @@ class CourseBlock(
|
||||
except InvalidTabsException as err:
|
||||
raise type(err)(f'{str(err)} For course: {str(self.id)}') # lint-amnesty, pylint: disable=line-too-long
|
||||
|
||||
if not settings.FEATURES.get("ENABLE_V2_CERT_DISPLAY_SETTINGS"):
|
||||
self.set_default_certificate_available_date()
|
||||
|
||||
def set_grading_policy(self, course_policy):
|
||||
"""
|
||||
The JSON object can have the keys GRADER and GRADE_CUTOFFS. If either is
|
||||
|
||||
Reference in New Issue
Block a user