diff --git a/lms/djangoapps/teams/csv.py b/lms/djangoapps/teams/csv.py index 0c61e66aa1..bebc66e2c6 100644 --- a/lms/djangoapps/teams/csv.py +++ b/lms/djangoapps/teams/csv.py @@ -9,6 +9,7 @@ from django.contrib.auth.models import User from lms.djangoapps.teams.api import OrganizationProtectionStatus, user_organization_protection_status from lms.djangoapps.teams.models import CourseTeam, CourseTeamMembership +from lms.djangoapps.program_enrollments.models import ProgramEnrollment from student.models import CourseEnrollment from .utils import emit_team_event @@ -420,6 +421,11 @@ class TeamMembershipImportManager(object): try: return User.objects.get(email=user_name) except User.DoesNotExist: - self.validation_errors.append('User ' + user_name + ' does not exist.') - return None - # TODO - handle user key case + try: + user = ProgramEnrollment.objects.get(external_user_key=user_name).user + if user is None: + return None + return user + except ProgramEnrollment.DoesNotExist: + self.validation_errors.append('User name/email/external key: ' + user_name + ' does not exist.') + return None diff --git a/lms/djangoapps/teams/tests/test_views.py b/lms/djangoapps/teams/tests/test_views.py index 7f7f7def5a..20aedd435b 100644 --- a/lms/djangoapps/teams/tests/test_views.py +++ b/lms/djangoapps/teams/tests/test_views.py @@ -7,6 +7,7 @@ Tests for the teams API at the HTTP request level. import json import unittest from datetime import datetime +from uuid import UUID import ddt import pytz @@ -29,6 +30,7 @@ from openedx.core.djangoapps.django_comment_common.models import FORUM_ROLE_COMM from openedx.core.djangoapps.django_comment_common.utils import seed_permissions_roles from openedx.core.lib.teams_config import TeamsConfig from student.models import CourseEnrollment +from lms.djangoapps.program_enrollments.tests.factories import ProgramEnrollmentFactory from student.tests.factories import AdminFactory, CourseEnrollmentFactory, UserFactory from util.testing import EventTestMixin from xmodule.modulestore.tests.django_utils import SharedModuleStoreTestCase @@ -500,7 +502,7 @@ class TeamAPITestCase(APITestCase, SharedModuleStoreTestCase): return self.build_membership_data_raw(self.users[username].username, team.team_id) @classmethod - def create_and_enroll_student(cls, courses=None, username=None, mode=None): + def create_and_enroll_student(cls, courses=None, username=None, mode=None, external_key=None): """ Creates a new student and enrolls that student in the course. Adds the new user to the cls.users dictionary with the username as the key. @@ -516,6 +518,15 @@ class TeamAPITestCase(APITestCase, SharedModuleStoreTestCase): CourseEnrollment.enroll(user, course.id, mode=mode, check_access=True) cls.users[user.username] = user + if external_key is not None: + ProgramEnrollmentFactory( + user=user, + external_user_key=external_key, + program_uuid=UUID("88888888-4444-3333-1111-000000000000"), + curriculum_uuid=UUID("77777777-4444-2222-1111-000000000000"), + status='enrolled' + ) + return user.username def login(self, user): @@ -2748,3 +2759,38 @@ class TestBulkMembershipManagement(TeamAPITestCase): user_id=self.users[username].id, team__name=nuclear_team_name ).exists()) + + def test_create_membership_via_upload_using_external_key(self): + self.create_and_enroll_student(username='a_user', external_key='a_user_external_key') + csv_content = 'user,mode,topic_0' + '\n' + csv_content += 'a_user_external_key,audit,team wind power' + csv_file = SimpleUploadedFile('test_file.csv', csv_content.encode('utf8'), content_type='text/csv') + self.client.login(username=self.users['course_staff'].username, password=self.users['course_staff'].password) + response = self.make_call( + reverse('team_membership_bulk_management', args=[self.good_course_id]), + 201, + method='post', + data={'csv': csv_file}, + user='staff' + ) + response_text = json.loads(response.content.decode('utf-8')) + self.assertEqual(response_text['message'], '1 learners were affected.') + + def test_create_membership_via_upload_using_external_key_invalid(self): + self.create_and_enroll_student(username='a_user', external_key='a_user_external_key') + csv_content = 'user,mode,topic_0' + '\n' + csv_content += 'a_user_external_key_invalid,audit,team wind power' + csv_file = SimpleUploadedFile('test_file.csv', csv_content.encode('utf8'), content_type='text/csv') + self.client.login(username=self.users['course_staff'].username, password=self.users['course_staff'].password) + response = self.make_call( + reverse('team_membership_bulk_management', args=[self.good_course_id]), + 400, + method='post', + data={'csv': csv_file}, + user='staff' + ) + response_text = json.loads(response.content.decode('utf-8')) + self.assertEqual( + response_text['errors'], + ['User name/email/external key: a_user_external_key_invalid does not exist.'] + )