Files
edx-platform/lms/djangoapps/survey/tests/test_models.py
2021-03-19 22:42:14 +05:00

311 lines
10 KiB
Python

"""
Python tests for the Survey models
"""
from collections import OrderedDict
import ddt
import pytest
from django.contrib.auth.models import User # lint-amnesty, pylint: disable=imported-auth-user
from django.core.exceptions import ValidationError
from django.test import TestCase
from django.test.client import Client
from lms.djangoapps.survey.exceptions import SurveyFormNameAlreadyExists, SurveyFormNotFound
from lms.djangoapps.survey.models import SurveyAnswer, SurveyForm
@ddt.ddt
class SurveyModelsTests(TestCase):
"""
All tests for the Survey models.py file
"""
def setUp(self):
"""
Set up the test data used in the specific tests
"""
super().setUp()
self.client = Client()
# Create two accounts
self.password = 'abc'
self.student = User.objects.create_user('student', 'student@test.com', self.password)
self.student2 = User.objects.create_user('student2', 'student2@test.com', self.password)
self.test_survey_name = 'TestForm'
self.test_form = '<li><input name="field1" /></li><li><input name="field2" /></li><li><select name="ddl"><option>1</option></select></li>' # lint-amnesty, pylint: disable=line-too-long
self.test_form_update = '<input name="field1" />'
self.course_id = 'foo/bar/baz'
self.student_answers = OrderedDict({
'field1': 'value1',
'field2': 'value2',
})
self.student_answers_update = OrderedDict({
'field1': 'value1-updated',
'field2': 'value2-updated',
})
self.student_answers_update2 = OrderedDict({
'field1': 'value1-updated2',
})
self.student2_answers = OrderedDict({
'field1': 'value3'
})
def _create_test_survey(self):
"""
Helper method to set up test form
"""
return SurveyForm.create(self.test_survey_name, self.test_form)
def test_form_not_found_raise_exception(self):
"""
Asserts that when looking up a form that does not exist
"""
with pytest.raises(SurveyFormNotFound):
SurveyForm.get(self.test_survey_name)
def test_form_not_found_none(self):
"""
Asserts that when looking up a form that does not exist
"""
assert SurveyForm.get(self.test_survey_name, throw_if_not_found=False) is None
def test_create_new_form(self):
"""
Make sure we can create a new form a look it up
"""
survey = self._create_test_survey()
assert survey is not None
new_survey = SurveyForm.get(self.test_survey_name)
assert new_survey is not None
assert new_survey.form == self.test_form
def test_unicode_rendering(self):
"""
See if the survey form returns the expected unicode string
"""
survey = self._create_test_survey()
assert survey is not None
assert str(survey) == self.test_survey_name
def test_create_form_with_malformed_html(self):
"""
Make sure that if a SurveyForm is saved with unparseable html
an exception is thrown
"""
with pytest.raises(ValidationError):
SurveyForm.create('badform', '<input name="oops" /><<<>')
def test_create_form_with_no_fields(self):
"""
Make sure that if a SurveyForm is saved without any named fields
an exception is thrown
"""
with pytest.raises(ValidationError):
SurveyForm.create('badform', '<p>no input fields here</p>')
with pytest.raises(ValidationError):
SurveyForm.create('badform', '<input id="input_without_name" />')
def test_create_form_already_exists(self):
"""
Make sure we can't create two surveys of the same name
"""
self._create_test_survey()
with pytest.raises(SurveyFormNameAlreadyExists):
self._create_test_survey()
def test_create_form_update_existing(self):
"""
Make sure we can update an existing form
"""
survey = self._create_test_survey()
assert survey is not None
survey = SurveyForm.create(self.test_survey_name, self.test_form_update, update_if_exists=True)
assert survey is not None
survey = SurveyForm.get(self.test_survey_name)
assert survey is not None
assert survey.form == self.test_form_update
def test_survey_has_no_answers(self):
"""
Create a new survey and assert that there are no answers to that survey
"""
survey = self._create_test_survey()
assert len(survey.get_answers()) == 0
def test_user_has_no_answers(self):
"""
Create a new survey with no answers in it and check that a user is determined to not have answered it
"""
survey = self._create_test_survey()
assert not survey.has_user_answered_survey(self.student)
assert len(survey.get_answers()) == 0
@ddt.data(None, 'foo/bar/baz')
def test_single_user_answers(self, course_id):
"""
Create a new survey and add answers to it
"""
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, course_id)
assert survey.has_user_answered_survey(self.student)
all_answers = survey.get_answers()
assert len(list(all_answers.keys())) == 1
assert self.student.id in all_answers
assert all_answers[self.student.id] == self.student_answers
answers = survey.get_answers(self.student)
assert len(list(answers.keys())) == 1
assert self.student.id in answers
assert all_answers[self.student.id] == self.student_answers
# check that the course_id was set
answer_objs = SurveyAnswer.objects.filter(
user=self.student,
form=survey
)
for answer_obj in answer_objs:
if course_id:
assert str(answer_obj.course_key) == course_id
else:
assert answer_obj.course_key is None
def test_multiple_user_answers(self):
"""
Create a new survey and add answers to it
"""
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, self.course_id)
survey.save_user_answers(self.student2, self.student2_answers, self.course_id)
assert survey.has_user_answered_survey(self.student)
all_answers = survey.get_answers()
assert len(list(all_answers.keys())) == 2
assert self.student.id in all_answers
assert self.student2.id in all_answers
assert all_answers[self.student.id] == self.student_answers
assert all_answers[self.student2.id] == self.student2_answers
answers = survey.get_answers(self.student)
assert len(list(answers.keys())) == 1
assert self.student.id in answers
assert answers[self.student.id] == self.student_answers
answers = survey.get_answers(self.student2)
assert len(list(answers.keys())) == 1
assert self.student2.id in answers
assert answers[self.student2.id] == self.student2_answers
def test_update_answers(self):
"""
Make sure the update case works
"""
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, self.course_id)
answers = survey.get_answers(self.student)
assert len(list(answers.keys())) == 1
assert self.student.id in answers
assert answers[self.student.id] == self.student_answers
# update
survey.save_user_answers(self.student, self.student_answers_update, self.course_id)
answers = survey.get_answers(self.student)
assert len(list(answers.keys())) == 1
assert self.student.id in answers
assert answers[self.student.id] == self.student_answers_update
# update with just a subset of the origin dataset
survey.save_user_answers(self.student, self.student_answers_update2, self.course_id)
answers = survey.get_answers(self.student)
assert len(list(answers.keys())) == 1
assert self.student.id in answers
assert answers[self.student.id] == self.student_answers_update2
def test_limit_num_users(self):
"""
Verify that the limit_num_users parameter to get_answers()
works as intended
"""
survey = self._create_test_survey()
survey.save_user_answers(self.student, self.student_answers, self.course_id)
survey.save_user_answers(self.student2, self.student2_answers, self.course_id)
# even though we have 2 users submitted answers
# limit the result set to just 1
all_answers = survey.get_answers(limit_num_users=1)
assert len(list(all_answers.keys())) == 1
def test_get_field_names(self):
"""
Create a new survey and add answers to it
"""
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, self.course_id)
survey.save_user_answers(self.student2, self.student2_answers, self.course_id)
names = survey.get_field_names()
assert sorted(names) == ['ddl', 'field1', 'field2']
def test_retire_user_successful(self):
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, self.course_id)
survey.save_user_answers(self.student2, self.student2_answers, self.course_id)
retire_result = SurveyAnswer.retire_user(self.student.id)
assert retire_result
answers = survey.get_answers(self.student)
blanked_out_student_answser = {key: '' for key in self.student_answers}
assert answers[self.student.id] == blanked_out_student_answser
assert survey.get_answers(self.student2)[self.student2.id] == self.student2_answers
def test_retire_user_not_exist(self):
survey = self._create_test_survey()
assert survey is not None
survey.save_user_answers(self.student, self.student_answers, self.course_id)
retire_result = SurveyAnswer.retire_user(self.student2.id)
assert not retire_result
answers = survey.get_answers(self.student)
assert answers[self.student.id] == self.student_answers