def check_user_data_correctness(self): username_to_user = {} for user_data in self.users.values(): if user_data.username in username_to_user: self.errors.append(_('The imported data contains two email addresses with the same username ' + _("('{}' and '{}').")).format(user_data.email, username_to_user[user_data.username].email)) username_to_user[user_data.username] = user_data for user_data in self.users.values(): if not is_external_email(user_data.email) and user_data.username == "": self.errors.append(_('Emailaddress {}: Username cannot be empty for non-external users.').format(user_data.email)) return # to avoid duplicate errors with validate try: user_data.validate() except ValidationError as e: self.errors.append(_('User {}: Error when validating: {}').format(user_data.email, e)) try: duplicate_email_user = UserProfile.objects.get(email=user_data.email) if duplicate_email_user.username != user_data.username: self.errors.append(_('User {}, username {}: Another user with the same email address and a ' 'different username ({}) already exists.').format(user_data.email, user_data.username, duplicate_email_user.username)) except UserProfile.DoesNotExist: pass if not is_external_email(user_data.email) and len(user_data.username) > settings.INTERNAL_USERNAMES_MAX_LENGTH : self.errors.append(_('User {}: Username cannot be longer than {} characters for non-external users.').format(user_data.email, settings.INTERNAL_USERNAMES_MAX_LENGTH)) if user_data.first_name == "": self.errors.append(_('User {}: First name is missing.').format(user_data.email)) if user_data.last_name == "": self.errors.append(_('User {}: Last name is missing.').format(user_data.email))
def check_user_data_correctness(self): username_to_user = {} for user_data in self.users.values(): if user_data.username in username_to_user: self.errors.append(_('The imported data contains two email addresses with the same username ' + _("('{}' and '{}').")).format(user_data.email, username_to_user[user_data.username].email)) username_to_user[user_data.username] = user_data for user_data in self.users.values(): if not is_external_email(user_data.email) and user_data.username == "": self.errors.append(_('Emailaddress {}: Username cannot be empty for non-external users.').format(user_data.email)) return # to avoid duplicate errors with validate try: user_data.validate() except ValidationError as e: self.errors.append(_('User {}: Error when validating: {}').format(user_data.email, e)) try: duplicate_email_user = UserProfile.objects.get(email=user_data.email) if duplicate_email_user.username != user_data.username: self.errors.append(_('User {}, username {}: Another user with the same email address and a ' 'different username ({}) already exists.').format(user_data.email, user_data.username, duplicate_email_user.username)) except UserProfile.DoesNotExist: pass if not is_external_email(user_data.email) and len(user_data.username) > settings.INTERNAL_USERNAMES_MAX_LENGTH: self.errors.append(_('User {}: Username cannot be longer than {} characters for non-external users.').format(user_data.email, settings.INTERNAL_USERNAMES_MAX_LENGTH)) if user_data.first_name == "": # This might be meaningless due to an empty email, but in that case, there will be # another error saying that the email address is missing for this user. self.errors.append(_('User {}: First name is missing.').format(user_data.email)) if user_data.last_name == "": self.errors.append(_('User {}: Last name is missing.').format(user_data.email))
def is_external(self): # do the import here to prevent a circular import from evap.evaluation.tools import is_external_email if not self.email: return True return is_external_email(self.email)
def generate_external_usernames_if_external(self): for user_data in self.users.values(): if is_external_email(user_data.email): if user_data.username != "": self.errors.append(_('User {}: Username must be empty for external users.').format(user_data.username)) username = (user_data.first_name + '.' + user_data.last_name + '.ext').lower() for old, new in settings.USERNAME_REPLACEMENTS: username = username.replace(old, new) user_data.username = username
def __init__(self, username='', first_name='', last_name='', title='', email=''): self.username = username.strip().lower() self.first_name = first_name.strip() self.last_name = last_name.strip() self.title = title.strip() self.email = email.strip().lower() self.is_external = False if is_external_email(self.email): self.is_external = True if self.username == '': self.username = (self.first_name + '.' + self.last_name + '.ext').lower()
def check_user_data_correctness(self): for user_data in self.users.values(): if not is_external_email(user_data.email) and user_data.username == "": self.errors.append( _(u"Emailaddress {}: Username cannot be empty for non-external users.").format(user_data.email) ) return # to avoid duplicate errors with validate try: user_data.validate() except ValidationError as e: self.errors.append(_(u"User {}: Error when validating: {}").format(user_data.email, e)) if ( not is_external_email(user_data.email) and len(user_data.username) > settings.INTERNAL_USERNAMES_MAX_LENGTH ): self.errors.append( _(u"User {}: Username cannot be longer than {} characters for non-external users.").format( user_data.email, settings.INTERNAL_USERNAMES_MAX_LENGTH ) ) if user_data.first_name == "": self.errors.append(_(u"User {}: First name is missing.").format(user_data.email)) if user_data.last_name == "": self.errors.append(_(u"User {}: Last name is missing.").format(user_data.email))
def email_needs_login_key(cls, email): # do the import here to prevent a circular import from evap.evaluation.tools import is_external_email return is_external_email(email)
def email_needs_login_key(cls, email): from evap.evaluation.tools import is_external_email return is_external_email(email)
def bulk_update_users(request, user_file_content, test_run): # pylint: disable=too-many-branches,too-many-locals # user_file must have one user per line in the format "{username},{email}" imported_emails = { clean_email(line.decode().split(',')[1]) for line in user_file_content.splitlines() } emails_of_users_to_be_created = [] users_to_be_updated = [] skipped_external_emails_counter = 0 for imported_email in imported_emails: if is_external_email(imported_email): skipped_external_emails_counter += 1 continue try: matching_user = find_matching_internal_user_for_email( request, imported_email) except UserProfile.MultipleObjectsReturned as e: messages.error( request, format_html( _('Multiple users match the email {}:{}'), imported_email, create_user_list_html_string_for_message(e.args[0]))) return False if not matching_user: emails_of_users_to_be_created.append(imported_email) elif matching_user.email != imported_email: users_to_be_updated.append((matching_user, imported_email)) emails_of_non_obsolete_users = set(imported_emails) | { user.email for user, _ in users_to_be_updated } deletable_users, users_to_mark_inactive = [], [] for user in UserProfile.objects.exclude( email__in=emails_of_non_obsolete_users): if user.can_be_deleted_by_manager: deletable_users.append(user) elif user.is_active and user.can_be_marked_inactive_by_manager: users_to_mark_inactive.append(user) messages.info( request, _('The uploaded text file contains {} internal and {} external users. The external users will be ignored. ' '{} users are currently in the database. Of those, {} will be updated, {} will be deleted and {} will be ' 'marked inactive. {} new users will be created.').format( len(imported_emails) - skipped_external_emails_counter, skipped_external_emails_counter, UserProfile.objects.count(), len(users_to_be_updated), len(deletable_users), len(users_to_mark_inactive), len(emails_of_users_to_be_created))) if users_to_be_updated: messages.info( request, format_html( _('Users to be updated are:{}'), format_html_join( '', '<br />{} {} ({} > {})', ((user.first_name, user.last_name, user.email, email) for user, email in users_to_be_updated)))) if deletable_users: messages.info( request, format_html( _('Users to be deleted are:{}'), create_user_list_html_string_for_message(deletable_users))) if users_to_mark_inactive: messages.info( request, format_html( _('Users to be marked inactive are:{}'), create_user_list_html_string_for_message( users_to_mark_inactive))) if emails_of_users_to_be_created: messages.info( request, format_html( _('Users to be created are:{}'), format_html_join( '', '<br />{}', ((email, ) for email in emails_of_users_to_be_created)))) with transaction.atomic(): for user in deletable_users + users_to_mark_inactive: for message in remove_user_from_represented_and_ccing_users( user, deletable_users + users_to_mark_inactive, test_run): messages.warning(request, message) if test_run: messages.info(request, _('No data was changed in this test run.')) else: for user in deletable_users: user.delete() for user in users_to_mark_inactive: user.is_active = False user.save() for user, email in users_to_be_updated: user.email = email user.save() userprofiles_to_create = [] for email in emails_of_users_to_be_created: userprofiles_to_create.append(UserProfile(email=email)) UserProfile.objects.bulk_create(userprofiles_to_create) messages.success(request, _('Users have been successfully updated.')) return True