summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--yaksh/file_utils.py5
-rw-r--r--yaksh/test_views.py35
-rw-r--r--yaksh/views.py53
3 files changed, 47 insertions, 46 deletions
diff --git a/yaksh/file_utils.py b/yaksh/file_utils.py
index 0d80b8f..7aef249 100644
--- a/yaksh/file_utils.py
+++ b/yaksh/file_utils.py
@@ -52,6 +52,7 @@ def extract_files(zip_file, path=None):
def is_csv(document):
+ ''' Check if document is csv with ',' as the delimiter'''
try:
try:
content = document.read(1024).decode('utf-8')
@@ -62,8 +63,8 @@ def is_csv(document):
dialect = sniffer.sniff(content)
document.seek(0)
except (csv.Error, UnicodeDecodeError):
- return False
- return True
+ return False, None
+ return True, dialect
def headers_present(dict_reader, headers):
diff --git a/yaksh/test_views.py b/yaksh/test_views.py
index 465fb30..9f46ba9 100644
--- a/yaksh/test_views.py
+++ b/yaksh/test_views.py
@@ -1792,21 +1792,20 @@ class TestCourseDetail(TestCase):
self.student.delete()
self.user1_course.delete()
-
def test_upload_users_with_correct_csv(self):
# Given
self.client.login(
username=self.user1.username,
password=self.user1_plaintext_pass
)
- csv_file_path = os.path.join(settings.FIXTURE_DIRS, "users_correct.csv")
+ csv_file_path = os.path.join(FIXTURES_DIR_PATH, "users_correct.csv")
csv_file = open(csv_file_path, 'rb')
upload_file = SimpleUploadedFile(csv_file_path, csv_file.read())
# When
response = self.client.post(reverse('yaksh:upload_users',
- kwargs={'course_id': self.user1_course.id}),
- data={'csv_file': upload_file})
+ kwargs={'course_id': self.user1_course.id}),
+ data={'csv_file': upload_file})
csv_file.close()
# Then
@@ -1816,22 +1815,21 @@ class TestCourseDetail(TestCase):
self.assertIn('upload_details', response.context)
self.assertTemplateUsed(response, 'yaksh/course_detail.html')
-
def test_upload_users_with_wrong_csv(self):
# Given
self.client.login(
username=self.user1.username,
password=self.user1_plaintext_pass
)
- csv_file_path = os.path.join(settings.FIXTURE_DIRS, "demo_questions.zip")
+ csv_file_path = os.path.join(FIXTURES_DIR_PATH, "demo_questions.zip")
csv_file = open(csv_file_path, 'rb')
upload_file = SimpleUploadedFile(csv_file_path, csv_file.read())
message = "The file uploaded is not a CSV file."
# When
response = self.client.post(reverse('yaksh:upload_users',
- kwargs={'course_id': self.user1_course.id}),
- data={'csv_file': upload_file})
+ kwargs={'course_id': self.user1_course.id}),
+ data={'csv_file': upload_file})
csv_file.close()
# Then
@@ -1841,22 +1839,21 @@ class TestCourseDetail(TestCase):
self.assertEqual(response.context['message'], message)
self.assertTemplateUsed(response, 'yaksh/course_detail.html')
-
def test_upload_users_csv_with_missing_headers(self):
# Given
self.client.login(
username=self.user1.username,
password=self.user1_plaintext_pass
)
- csv_file_path = os.path.join(settings.FIXTURE_DIRS, "users_some_headers_missing.csv")
+ csv_file_path = os.path.join(FIXTURES_DIR_PATH, "users_some_headers_missing.csv")
csv_file = open(csv_file_path, 'rb')
upload_file = SimpleUploadedFile(csv_file_path, csv_file.read())
message = "The CSV file does not contain the required headers"
# When
response = self.client.post(reverse('yaksh:upload_users',
- kwargs={'course_id': self.user1_course.id}),
- data={'csv_file': upload_file})
+ kwargs={'course_id': self.user1_course.id}),
+ data={'csv_file': upload_file})
csv_file.close()
# Then
@@ -1872,14 +1869,14 @@ class TestCourseDetail(TestCase):
username=self.user1.username,
password=self.user1_plaintext_pass
)
- csv_file_path = os.path.join(settings.FIXTURE_DIRS, "users_with_no_values.csv")
+ csv_file_path = os.path.join(FIXTURES_DIR_PATH, "users_with_no_values.csv")
csv_file = open(csv_file_path, 'rb')
upload_file = SimpleUploadedFile(csv_file_path, csv_file.read())
# When
response = self.client.post(reverse('yaksh:upload_users',
- kwargs={'course_id': self.user1_course.id}),
- data={'csv_file': upload_file})
+ kwargs={'course_id': self.user1_course.id}),
+ data={'csv_file': upload_file})
csv_file.close()
# Then
@@ -1889,7 +1886,6 @@ class TestCourseDetail(TestCase):
self.assertIn("No rows in the CSV file", response.context['upload_details'])
self.assertTemplateUsed(response, 'yaksh/course_detail.html')
-
def test_upload_users_csv_with_missing_values(self):
'''
This test takes csv with 3 row values.
@@ -1908,14 +1904,14 @@ class TestCourseDetail(TestCase):
username=self.user1.username,
password=self.user1_plaintext_pass
)
- csv_file_path = os.path.join(settings.FIXTURE_DIRS, "users_some_values_missing.csv")
+ csv_file_path = os.path.join(FIXTURES_DIR_PATH, "users_some_values_missing.csv")
csv_file = open(csv_file_path, 'rb')
upload_file = SimpleUploadedFile(csv_file_path, csv_file.read())
# When
response = self.client.post(reverse('yaksh:upload_users',
- kwargs={'course_id': self.user1_course.id}),
- data={'csv_file': upload_file})
+ kwargs={'course_id': self.user1_course.id}),
+ data={'csv_file': upload_file})
csv_file.close()
# Then
@@ -1926,7 +1922,6 @@ class TestCourseDetail(TestCase):
self.assertNotIn('message', response.context)
self.assertTemplateUsed(response, 'yaksh/course_detail.html')
-
def test_course_detail_denies_anonymous(self):
"""
If not logged in redirect to login page
diff --git a/yaksh/views.py b/yaksh/views.py
index 71b4abe..61d2b5b 100644
--- a/yaksh/views.py
+++ b/yaksh/views.py
@@ -1856,49 +1856,54 @@ def upload_users(request, course_id):
if 'csv_file' not in request.FILES:
context['message'] = "Please upload a CSV file."
return my_render_to_response('yaksh/course_detail.html', context,
- context_instance=ci)
+ context_instance=ci)
csv_file = request.FILES['csv_file']
- if not is_csv(csv_file):
+ is_csv_file, dialect = is_csv(csv_file)
+ if not is_csv_file:
context['message'] = "The file uploaded is not a CSV file."
return my_render_to_response('yaksh/course_detail.html', context,
- context_instance=ci)
- headers = {'firstname':'', 'lastname':'', 'email':''}
- reader = csv.DictReader(csv_file.read().decode('utf-8').splitlines())
+ context_instance=ci)
+ headers = {'firstname': '', 'lastname': '', 'email': ''}
+ try:
+ reader = csv.DictReader(csv_file.read().decode('utf-8').splitlines(),
+ dialect=dialect)
+ except TypeError:
+ context['message'] = "Bad CSV file"
+ return my_render_to_response('yaksh/course_detail.html', context,
+ context_instance=ci)
if not headers_present(reader, headers):
context['message'] = "The CSV file does not contain the required headers"
return my_render_to_response('yaksh/course_detail.html', context,
- context_instance=ci)
+ context_instance=ci)
context['upload_details'] = _read_user_csv(reader, headers, course)
return my_render_to_response('yaksh/course_detail.html', context,
- context_instance=ci)
+ context_instance=ci)
def _read_user_csv(reader, headers, course):
upload_details = ["Upload Summary:"]
- counter = 0;
+ counter = 0
+ add_users = []
for row in reader:
counter += 1
email, first_name, last_name = map(str.strip, [row[headers['email']],
- row[headers['firstname']], row[headers['lastname']]])
+ row[headers['firstname']],
+ row[headers['lastname']]])
if not email or not first_name or not last_name:
upload_details.append("{0} -- Missing Values".format(counter))
continue
- user = User.objects.filter(email=email)
- if user.exists():
- upload_details.append("{0} -- {1} -- Email Already Exists".format(
- counter, email))
+ if User.objects.filter(Q(username=email) | Q(email=email)).exists():
+ upload_details.append("{0} -- {1} -- Email or Username Already \
+ Exists".format(counter, email))
else:
- try:
- user = User.objects.create_user(username=email, password=email,
- email=email, first_name=first_name, last_name=last_name)
- except IntegrityError:
- upload_details.append("{0} -- {1} -- User Already Exists".format(
- counter, email))
- else:
- Profile.objects.create(user=user, is_email_verified=True)
- course.students.add(user)
- upload_details.append("{0} -- {1} -- User Added Successfully".format(
- counter, email))
+ user = User.objects.create_user(username=email, password=email,
+ email=email, first_name=first_name,
+ last_name=last_name)
+ Profile.objects.create(user=user, is_email_verified=True)
+ add_users.append(user)
+ upload_details.append("{0} -- {1} -- User Added Successfully".format(
+ counter, email))
+ course.students.add(*add_users)
if counter == 0:
upload_details.append("No rows in the CSV file")
return upload_details