Update support form to make course required.

Update support form to auto select course and make course
selection required to submit form.

LEARNER-4254
This commit is contained in:
Waheed Ahmed
2018-04-18 17:59:38 +05:00
parent db5042f084
commit 2c09ebb208
10 changed files with 59 additions and 21 deletions

View File

@@ -5,6 +5,7 @@ Middleware for the courseware app
from django.shortcuts import redirect
from lms.djangoapps.courseware.exceptions import Redirect
from util.request import COURSE_REGEX
class RedirectMiddleware(object):
@@ -17,3 +18,20 @@ class RedirectMiddleware(object):
"""
if isinstance(exception, Redirect):
return redirect(exception.url)
class CacheCourseIdMiddleware(object):
"""Middleware that adds course_id to user request session."""
def process_request(self, request):
"""
Add a course_id to user request session.
"""
if request.user.is_authenticated():
match = COURSE_REGEX.match(request.build_absolute_uri())
course_id = None
if match:
course_id = match.group('course_id')
if course_id and course_id != request.session.get('course_id'):
request.session['course_id'] = course_id

View File

@@ -203,8 +203,8 @@ class IndexQueryTestCase(ModuleStoreTestCase):
NUM_PROBLEMS = 20
@ddt.data(
(ModuleStoreEnum.Type.mongo, 10, 143),
(ModuleStoreEnum.Type.split, 4, 143),
(ModuleStoreEnum.Type.mongo, 10, 146),
(ModuleStoreEnum.Type.split, 4, 146),
)
@ddt.unpack
def test_index_query_counts(self, store_type, expected_mongo_query_count, expected_mysql_query_count):
@@ -1424,17 +1424,21 @@ class ProgressPageTests(ProgressPageBaseTests):
resp = self._get_progress_page()
self.assertContains(resp, u"Download Your Certificate")
@ddt.data(True, False)
def test_progress_queries_paced_courses(self, self_paced):
@ddt.data(
(True, 37),
(False, 36)
)
@ddt.unpack
def test_progress_queries_paced_courses(self, self_paced, query_count):
"""Test that query counts remain the same for self-paced and instructor-paced courses."""
self.setup_course(self_paced=self_paced)
with self.assertNumQueries(34 if self_paced else 33, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST), check_mongo_calls(1):
with self.assertNumQueries(query_count, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST), check_mongo_calls(1):
self._get_progress_page()
@patch.dict(settings.FEATURES, {'ASSUME_ZERO_GRADE_IF_ABSENT_FOR_ALL_TESTS': False})
@ddt.data(
(False, 40, 27),
(True, 33, 23)
(False, 43, 27),
(True, 36, 23)
)
@ddt.unpack
def test_progress_queries(self, enable_waffle, initial, subsequent):

View File

@@ -406,8 +406,8 @@ class ViewsQueryCountTestCase(
return inner
@ddt.data(
(ModuleStoreEnum.Type.mongo, 3, 4, 32),
(ModuleStoreEnum.Type.split, 3, 13, 32),
(ModuleStoreEnum.Type.mongo, 3, 4, 35),
(ModuleStoreEnum.Type.split, 3, 13, 35),
)
@ddt.unpack
@count_queries
@@ -415,8 +415,8 @@ class ViewsQueryCountTestCase(
self.create_thread_helper(mock_request)
@ddt.data(
(ModuleStoreEnum.Type.mongo, 3, 3, 28),
(ModuleStoreEnum.Type.split, 3, 10, 28),
(ModuleStoreEnum.Type.mongo, 3, 3, 31),
(ModuleStoreEnum.Type.split, 3, 10, 31),
)
@ddt.unpack
@count_queries

View File

@@ -10,7 +10,11 @@ function LoggedInUser({ userInformation, setErrorState, zendeskApiHost, submitFo
if (userInformation.enrollments) {
courseElement = (<div>
<label className="label-course" htmlFor="course">{gettext('Course Name')}</label>
<select className="form-control select-course" id="course">
<select className="form-control select-course" id="course" value={userInformation.course_id}>
<option key="select-course" value="">--------</option>
<option key="not-course-specific" value="Not specific to a course">
{gettext('Not specific to a course')}
</option>
{userInformation.enrollments.map(enrollment =>
(<option key={enrollment.course_id} value={enrollment.course_id}>
{enrollment.course_name}
@@ -20,7 +24,7 @@ function LoggedInUser({ userInformation, setErrorState, zendeskApiHost, submitFo
</div>);
} else {
courseElement = (<div>
<label htmlFor="course">{gettext('Course Name')}<span> {gettext('(Optional)')}</span></label>
<label htmlFor="course">{gettext('Course Name')}</label>
<input type="text" className="form-control" id="course" />
</div>);
}

View File

@@ -41,9 +41,11 @@ class RenderForm extends React.Component {
body: $('#message').val(),
},
tags: this.props.context.tags,
};
},
errors = [];
let course;
this.clearErrors();
data.requester = {
email: $userInfo.data('email'),
@@ -54,13 +56,16 @@ class RenderForm extends React.Component {
if (!course) {
course = $course.val();
}
if (!course) {
$('#course').closest('.form-group').addClass('has-error');
errors.push(gettext('Select a course or select "Not specific to a course" for your support request.'));
}
data.custom_fields = [{
id: this.props.context.customFields.course_id,
value: course,
}];
if (this.validateData(data)) {
if (this.validateData(data, errors)) {
request.open('POST', url, true);
request.setRequestHeader('Content-type', 'application/json;charset=UTF-8');
request.setRequestHeader('X-CSRFToken', $.cookie('csrftoken'));
@@ -81,8 +86,12 @@ class RenderForm extends React.Component {
}
}
validateData(data) {
const errors = [];
clearErrors() {
this.setErrorState([]);
$('.form-group').removeClass('has-error');
}
validateData(data, errors) {
if (!data.subject) {
errors.push(gettext('Enter a subject for your support request.'));
$('#subject').closest('.form-group').addClass('has-error');

View File

@@ -32,6 +32,7 @@ class ContactUsView(View):
tags.append("site_name_{site}".format(site=current_site_name))
if request.user.is_authenticated():
context['course_id'] = request.session.get('course_id', '')
context['user_enrollments'] = CourseEnrollment.enrollments_for_user_with_overviews_preload(request.user)
enterprise_learner_data = enterprise_api.get_enterprise_learner_data(user=request.user)
if enterprise_learner_data:

View File

@@ -1288,6 +1288,7 @@ MIDDLEWARE_CLASSES = [
'django.middleware.clickjacking.XFrameOptionsMiddleware',
# to redirected unenrolled students to the course info page
'courseware.middleware.CacheCourseIdMiddleware',
'courseware.middleware.RedirectMiddleware',
'course_wiki.middleware.WikiAccessMiddleware',

View File

@@ -42,7 +42,8 @@ from openedx.core.djangolib.js_utils import js_escaped_string, dump_js_escaped_j
% if user.is_authenticated():
context['user'] = {
'username': "${user.username | n, js_escaped_string}",
'email': "${user.email | n, js_escaped_string}"
'email': "${user.email | n, js_escaped_string}",
'course_id': "${course_id | n, js_escaped_string}"
}
% if user_enrollments:

View File

@@ -175,7 +175,7 @@ class TestCourseHomePage(CourseHomePageTestCase):
course_home_url(self.course)
# Fetch the view and verify the query counts
with self.assertNumQueries(50, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST):
with self.assertNumQueries(53, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST):
with check_mongo_calls(4):
url = course_home_url(self.course)
self.client.get(url)

View File

@@ -126,7 +126,7 @@ class TestCourseUpdatesPage(SharedModuleStoreTestCase):
course_updates_url(self.course)
# Fetch the view and verify that the query counts haven't changed
with self.assertNumQueries(30, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST):
with self.assertNumQueries(33, table_blacklist=QUERY_COUNT_TABLE_BLACKLIST):
with check_mongo_calls(4):
url = course_updates_url(self.course)
self.client.get(url)