def validate(self, attrs): """ Check that the cohorts list is the same size as the courses list. """ if attrs.get('cohorts'): if attrs['action'] != 'enroll': raise serializers.ValidationError("Cohorts can only be used for enrollments.") if len(attrs['cohorts']) != len(attrs['courses']): raise serializers.ValidationError( "If provided, the cohorts and courses should have equal number of items.") for course_id, cohort_name in zip(attrs['courses'], attrs['cohorts']): if not is_cohort_exists(course_key=CourseKey.from_string(course_id), name=cohort_name): raise serializers.ValidationError(u"cohort {cohort_name} not found in course {course_id}.".format( cohort_name=cohort_name, course_id=course_id) ) return attrs
def post(self, request): log.info(request.data) username = request.data.get('username') try: user = User.objects.get(username=username) except ObjectDoesNotExist: log.error(u"User {username} does not exist".format(username=username)) return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"User {username} does not exist".format(username=username)} ) course_id = request.data.get('course_id') if not course_id: log.error(u"Course ID must be specified to create a new enrollment.") return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Course ID must be specified to create a new enrollment."} ) try: course_key = CourseKey.from_string(course_id) except InvalidKeyError: log.error(u"No course '{course_id}' found for enrollment".format(course_id=course_id)) return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": u"No course '{course_id}' found for enrollment".format(course_id=course_id) } ) course_is_cohorted = is_course_cohorted(course_key) if not course_is_cohorted: log.info(u"Course {course_id} is not cohorted.".format(course_id=course_id)) return Response( status=status.HTTP_200_OK, data={"message": u"Course {course_id} is not cohorted.".format(course_id=course_id)} ) action = request.data.get('action') if action not in [u'add', u'delete']: log.error(u"Available actions are 'add' and 'delete'.") return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Available actions are 'add' and 'delete'."} ) cohort_exists = is_cohort_exists(course_key, VERIFIED) if not cohort_exists: if action == u'add': log.info(u"Cohort VERIFIED doesn't exist for course {} so let's create it!".format(course_id)) cohort = add_cohort(course_key, VERIFIED, 'manual') log.info(u"Cohort VEIFIED created for the course {}".format(course_id)) else: log.info(u"There aren't cohort verified for {course_id}".format(course_id=course_id)) return Response( status=status.HTTP_200_OK, data={"message": u"There aren't cohort verified for {course_id}".format(course_id=course_id)} ) else: cohort = get_cohort_by_name(course_key, VERIFIED) enrollment = CourseEnrollment.objects.get( user__username=username, course_id=course_key ) if not enrollment or not enrollment.is_active: if action == u'add': log.error(u"Failed to add user into verified cohort. User {username} not enrolled or unenrolled in course {course_id}.".format(username=username, course_id=course_id)) return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"User {username} not enrolled or unenrolled in course {course_id}.".format( username=username, course_id=course_id )} ) if action == u'delete': if not enrollment: log.info(u"User {username} is not enrolled in course {course_id}. (!!!)".format(username=username, course_id=course_id)) return Response( status=status.HTTP_200_OK, data={"message": u"User {username} is not enrolled in course {course_id}. (!!!)".format( username=username, course_id=course_id )} ) else: log.info(u"User {username} was unenrolled from course {course_id}.".format(username=username, course_id=course_id)) return Response( status=status.HTTP_200_OK, data={"message": u"User {username} was unenrolled from course {course_id}.".format( username=username, course_id=course_id )} ) course_cohorts = CourseUserGroup.objects.filter( course_id=course_key, users__id=user.id, group_type=CourseUserGroup.COHORT ) default_group = None for group in CourseUserGroup.objects.filter(course_id=course_key, group_type=CourseUserGroup.COHORT): if group.name.lower() == "default" or group.name.lower() == "default group": default_group = group if not default_group: log.info(u"Cohort DEFAULT doesn't exist for course {} so let's create it!".format(course_id)) default_group = add_cohort(course_key, "Default Group", 'random') log.info(u"Cohort 'Default Group' succesfully created for the course {}".format(course_id)) # remove user from verified cohort and add to default if action == u'delete': # let's check, that user not already presented into other cohort if course_cohorts.exists(): if course_cohorts.first().name == default_group.name: log.warning( u"User {username} already present into default cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=default_group.name, course_id=course_id)) return Response( status=status.HTTP_200_OK, data={ "message": u"User {username} already present into default cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=default_group.name, course_id=course_id )} ) elif course_cohorts.first().name == VERIFIED: try: add_user_to_cohort(default_group, username) log.info( u"User {username} succesfully moved into default cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=default_group.name, course_id=course_id)) except ValueError: log.warning( u"User {username} already present into default cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=default_group.name, course_id=course_id)) return Response( status=status.HTTP_200_OK, data={ "message": u"User {username} moved into default cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=default_group.name, course_id=course_id )} ) else: log.warning(u"Moving user {username} into default cohort {cohort_name} from verified in course {course_id}".format(username=username, cohort_name=default_group.name, course_id=course_id)) try: add_user_to_cohort(default_group, username) log.info(u"User {username} succesfully moved into default cohort {cohort_name} in course {course_id}".format(username=username, cohort_name=default_group.name, course_id=course_id)) except ValueError: log.warning(u"User {username} already present into default cohort {cohort_name} in course {course_id}".format(username=username, cohort_name=default_group.name, course_id=course_id)) return Response( status=status.HTTP_200_OK, data={"message": u"User {username} already present in non-verified cohort {cohort_name} in course {course_id}".format( username=username, cohort_name=course_cohorts.first().name, course_id=course_id )} ) if action == u"add": message = add_user_into_verified_cohort(course_cohorts, cohort, user) if not message: message = u"User {username} added to cohort {cohort_name} into course {course_id}".format(username=user.username, cohort_name=cohort.name, course_id=course_id) log.info(message) return Response( status=status.HTTP_200_OK, data={"message":message} )
def post(self, request): """ Enrolls the list of users in a verified course mode. """ # Get the users, Course ID, and Mode from the request. users = request.data.get('users', []) if len(users) == 0: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Users must be specified to create a new enrollment."} ) course_id = request.data.get('course_details', {}).get('course_id') if not course_id: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Course ID must be specified to create a new enrollment."} ) try: course_key = CourseKey.from_string(course_id) except InvalidKeyError: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"No course '{course_id}' found for enrollment".format(course_id=course_id)} ) # use verified course mode by default mode = request.data.get('mode', CourseMode.VERIFIED) bad_users = [] list_users = [] for username in users: try: user = User.objects.get(username=username) list_users.append(user) except ObjectDoesNotExist: bad_users.append(username) if len(bad_users) > 0: return Response( status=status.HTTP_400_BAD_REQUEST, data={'message': u'Users: {} does not exist.'.format(', '.join(bad_users))} ) for user in list_users: embargo_response = embargo_api.get_embargo_response(request, course_key, user) if embargo_response: return embargo_response current_username = None try: is_active = request.data.get('is_active') # Check if the requested activation status is None or a Boolean if is_active is not None and not isinstance(is_active, bool): return Response( status=status.HTTP_400_BAD_REQUEST, data={'message': u"'{value}' is an invalid enrollment activation status.".format(value=is_active)} ) enrollment_attributes = request.data.get('enrollment_attributes') errors = False already_paid = [] # list of users with verified enrollment not_enrolled = [] # list of not enrolled yet or unenrolled users for username in users: current_username = username enrollment = api.get_enrollment(username, unicode(course_key)) if not enrollment: not_enrolled.append(username) elif enrollment['is_active'] is not True: not_enrolled.append(username) elif enrollment['mode'] == CourseMode.VERIFIED: already_paid.append(username) msg_paid = u"" msg_not_enrolled = u"" if len(already_paid) > 0: msg_paid = u'Users: {} already paid for course.'.format(', '.join(already_paid)) errors = True if len(not_enrolled) > 0: msg_not_enrolled = u'Users: {} not enrolled for course.'.format(', '.join(not_enrolled)) errors = True if errors: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": (u"'{course_id}'\n:{msg_paid}\n{msg_not_enrolled}").format( course_id=course_id, msg_paid=msg_paid, msg_not_enrolled=msg_not_enrolled ), }) # update for cohorts cohort_exists = is_cohort_exists(course_key, VERIFIED) if not cohort_exists: cohort = add_cohort(course_key, VERIFIED, 'manual') else: cohort = get_cohort_by_name(course_key, VERIFIED) for username in users: current_username = username api.update_enrollment(username, unicode(course_key), mode=mode, is_active=is_active) user = User.objects.get(username=username) course_cohorts = CourseUserGroup.objects.filter( course_id=cohort.course_id, users__id=user.id, group_type=CourseUserGroup.COHORT ) add_user_into_verified_cohort(course_cohorts, cohort, user) email_opt_in = request.data.get('email_opt_in', None) if email_opt_in is not None: org = course_key.org for username in users: update_email_opt_in(username, org, email_opt_in) return Response( status=status.HTTP_200_OK, data={ "message": u"Success for course '{course_id}'.".format(course_id=course_id) }) except CourseModeNotFoundError as error: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": ( u"The course mode '{mode}' is not available for course '{course_id}'." ).format(mode="verified", course_id=course_id), "course_details": error.data }) except CourseEnrollmentExistsError as error: return Response(data=error.enrollment) except CourseEnrollmentError: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": ( u"An error occurred while creating the new course enrollment for user " u"'{username}' in course '{course_id}'" ).format(username=current_username, course_id=course_id) } )
def post(self, request): username = request.DATA.get('username') try: user = User.objects.get(username=username) except ObjectDoesNotExist: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"User {username} does not exist".format(username=username)} ) course_id = request.DATA.get('course_id') if not course_id: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Course ID must be specified to create a new enrollment."} ) try: course_key = CourseKey.from_string(course_id) except InvalidKeyError: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": u"No course '{course_id}' found for enrollment".format(course_id=course_id) } ) course_is_cohorted = is_course_cohorted(course_key) if not course_is_cohorted: return Response( status=status.HTTP_200_OK, data={"message": u"Course {course_id} is not cohorted.".format(course_id=course_id)} ) action = request.DATA.get('action') if action not in [u'add', u'delete']: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Available actions are 'add' and 'delete'."} ) cohort_exists = is_cohort_exists(course_key, VERIFIED) if not cohort_exists: if action == u'add': cohort = add_cohort(course_key, VERIFIED, 'manual') else: return Response( status=status.HTTP_200_OK, data={"message": u"There aren't cohort verified for {course_id}".format(course_id=course_id)} ) else: cohort = get_cohort_by_name(course_key, VERIFIED) enrollment = CourseEnrollment.objects.get( user__username=username, course_id=course_key ) if not enrollment or not enrollment.is_active: if action == u'add': return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"User {username} not enrolled or unenrolled in course {course_id}.".format( username=username, course_id=course_id )} ) if action == u'delete': return Response( status=status.HTTP_200_OK, data={"message": u"User {username} not enrolled or unenrolled in course {course_id}.".format( username=username, course_id=course_id )} ) course_cohorts = CourseUserGroup.objects.filter( course_id=course_key, users__id=user.id, group_type=CourseUserGroup.COHORT ) # remove user from verified cohort if action == u'delete': if not course_cohorts.exists() or course_cohorts[0].name != cohort.name: return Response( status=status.HTTP_200_OK, data={"message": u"User {username} already was removed from cohort {cohort_name}".format( username=username, cohort_name=cohort.name )} ) else: cohort.users.remove(user) return Response( status=status.HTTP_200_OK, data={"message": u"User {username} removed from cohort {cohort_name}".format( username=username, cohort_name=cohort.name )} ) if course_cohorts.exists(): if course_cohorts[0] == cohort: return Response( status=status.HTTP_200_OK, data={"message": u"User {username} already present in cohort {cohort_name}".format( username=username, cohort_name=cohort.name )} ) add_user_into_verified_cohort(course_cohorts, cohort, user) return Response( status=status.HTTP_200_OK, data={"message": u"User {username} added to cohort {cohort_name}".format( username=user.username, cohort_name=cohort.name )} )
def post(self, request): """ Enrolls the list of users in a verified course mode. """ # Get the users, Course ID, and Mode from the request. users = request.DATA.get('users', []) if len(users) == 0: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Users must be specified to create a new enrollment."} ) course_id = request.DATA.get('course_details', {}).get('course_id') if not course_id: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"Course ID must be specified to create a new enrollment."} ) try: course_key = CourseKey.from_string(course_id) except InvalidKeyError: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": u"No course '{course_id}' found for enrollment".format(course_id=course_id)} ) # use verified course mode by default mode = request.DATA.get('mode', CourseMode.VERIFIED) bad_users = [] list_users = [] for username in users: try: user = User.objects.get(username=username) list_users.append(user) except ObjectDoesNotExist: bad_users.append(username) if len(bad_users) > 0: return Response( status=status.HTTP_400_BAD_REQUEST, data={'message': u'Users: {} does not exist.'.format(', '.join(bad_users))} ) for user in list_users: embargo_response = embargo_api.get_embargo_response(request, course_key, user) if embargo_response: return embargo_response current_username = None try: is_active = request.DATA.get('is_active') # Check if the requested activation status is None or a Boolean if is_active is not None and not isinstance(is_active, bool): return Response( status=status.HTTP_400_BAD_REQUEST, data={'message': u"'{value}' is an invalid enrollment activation status.".format(value=is_active)} ) enrollment_attributes = request.DATA.get('enrollment_attributes') errors = False already_paid = [] # list of users with verified enrollment not_enrolled = [] # list of not enrolled yet or unenrolled users for username in users: current_username = username enrollment = api.get_enrollment(username, unicode(course_key)) if not enrollment: not_enrolled.append(username) elif enrollment['is_active'] is not True: not_enrolled.append(username) elif enrollment['mode'] == CourseMode.VERIFIED: already_paid.append(username) msg_paid = u"" msg_not_enrolled = u"" if len(already_paid) > 0: msg_paid = u'Users: {} already paid for course.'.format(', '.join(already_paid)) errors = True if len(not_enrolled) > 0: msg_not_enrolled = u'Users: {} not enrolled for course.'.format(', '.join(not_enrolled)) errors = True if errors: return Response( status=status.HTTP_400_BAD_REQUEST, data={"message": (u"'{course_id}'\n:{msg_paid}\n{msg_not_enrolled}").format( course_id=course_id, msg_paid=msg_paid, msg_not_enrolled=msg_not_enrolled ), }) # update for cohorts cohort_exists = is_cohort_exists(course_key, VERIFIED) if not cohort_exists: cohort = add_cohort(course_key, VERIFIED, 'manual') else: cohort = get_cohort_by_name(course_key, VERIFIED) for username in users: current_username = username api.update_enrollment(username, unicode(course_key), mode=mode, is_active=is_active) user = User.objects.get(username=username) course_cohorts = CourseUserGroup.objects.filter( course_id=cohort.course_id, users__id=user.id, group_type=CourseUserGroup.COHORT ) add_user_into_verified_cohort(course_cohorts, cohort, user) email_opt_in = request.DATA.get('email_opt_in', None) if email_opt_in is not None: org = course_key.org for username in users: update_email_opt_in(username, org, email_opt_in) return Response( status=status.HTTP_200_OK, data={ "message": u"Success for course '{course_id}'.".format(course_id=course_id) }) except CourseModeNotFoundError as error: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": ( u"The course mode '{mode}' is not available for course '{course_id}'." ).format(mode="verified", course_id=course_id), "course_details": error.data }) except CourseNotFoundError: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": u"No course '{course_id}' found for enrollment".format(course_id=course_id) } ) except CourseEnrollmentExistsError as error: return Response(data=error.enrollment) except CourseEnrollmentError: return Response( status=status.HTTP_400_BAD_REQUEST, data={ "message": ( u"An error occurred while creating the new course enrollment for user " u"'{username}' in course '{course_id}'" ).format(username=current_username, course_id=course_id) } )