Exemple #1
0
    def set_password(self, raw_password=None, hashed_password=None, cached_password=None):
        """Set a password with the raw password string, or the pre-hashed password.
        If using the raw string, """
        assert hashed_password is None or settings.DEBUG, "Only use hashed_password in debug mode."
        assert raw_password is not None or hashed_password is not None, "Must be passing in raw or hashed password"
        assert not (raw_password is not None and hashed_password is not None), "Must be specifying only one--not both."

        if raw_password:
            verify_raw_password(raw_password)

        if hashed_password:
            self.password = hashed_password

            # Can't save a cached password from a hash, so just make sure there is none.
            # Note: Need to do this, even if they're not enabled--we don't want to risk
            #   being out of sync (if people turn on/off/on the feature
            CachedPassword.invalidate_cached_password(user=self)

        else:
            n_iters = (
                settings.PASSWORD_ITERATIONS_TEACHER_SYNCED
                if self.is_teacher
                else settings.PASSWORD_ITERATIONS_STUDENT_SYNCED
            )
            self.password = crypt(raw_password, iterations=n_iters)

            if self.id:
                CachedPassword.set_cached_password(self, raw_password)
Exemple #2
0
    def set_password(self,
                     raw_password=None,
                     hashed_password=None,
                     cached_password=None):
        """Set a password with the raw password string, or the pre-hashed password.
        If using the raw string, """
        assert hashed_password is None or settings.DEBUG, "Only use hashed_password in debug mode."
        assert raw_password is not None or hashed_password is not None, "Must be passing in raw or hashed password"
        assert not (raw_password is not None and hashed_password
                    is not None), "Must be specifying only one--not both."

        if raw_password:
            verify_raw_password(raw_password)

        if hashed_password:
            self.password = hashed_password

            # Can't save a cached password from a hash, so just make sure there is none.
            # Note: Need to do this, even if they're not enabled--we don't want to risk
            #   being out of sync (if people turn on/off/on the feature
            CachedPassword.invalidate_cached_password(user=self)

        else:
            n_iters = settings.PASSWORD_ITERATIONS_TEACHER_SYNCED if self.is_teacher else settings.PASSWORD_ITERATIONS_STUDENT_SYNCED
            self.password = crypt(raw_password, iterations=n_iters)

            if self.id:
                CachedPassword.set_cached_password(self, raw_password)
Exemple #3
0
    def clean(self):
        facility = self.cleaned_data.get('facility')
        username = self.cleaned_data.get('username', '')
        zone = self.cleaned_data.get('zone_fallback')

        # Don't allow (only through the form) the same username within the same facility, or conflicting with the admin.
        users_with_same_username = FacilityUser.objects.filter(username__iexact=username, facility=facility)
        username_taken = users_with_same_username.count() > 0
        username_changed = not self.instance or self.instance.username != username
        if username_taken and username_changed or User.objects.filter(username__iexact=username).count() > 0:
            self.set_field_error(field_name='username', message=_("A user with this username already exists. Please choose a new username and try again."))

        ## Check password
        password_first = self.cleaned_data.get('password_first', "")
        password_recheck = self.cleaned_data.get('password_recheck', "")
        # If they have put anything in the new password field, it must match the password check field
        if password_first != password_recheck:
            self.set_field_error(field_name='password_recheck', message=_("The passwords didn't match. Please re-enter the passwords."))

        # Next, enforce length if they submitted a password
        if password_first:
            try:
                verify_raw_password(password_first)
            except ValidationError as ve:
                # MUST: The ValidationError constructor sets the error message into a list with
                # `self.messages = [message]` so we get the first message from the list.  It
                # should have assigned the value to `self.message = message` too but maybe on
                # newer Django versions this is fixed.
                message = ''
                if hasattr(ve, 'messages') and isinstance(ve.messages, list) and ve.messages:
                    message = ve.messages[0]
                self.set_field_error(field_name='password_first', message=message)

        elif (self.instance and not self.instance.password) or password_first or password_recheck:
            # Only perform check on a new user or a password change
            if password_first != password_recheck:
                self.set_field_error(field_name='password_recheck', message=_("The passwords didn't match. Please re-enter the passwords."))

        ## Warn the user during sign up or adding user if a user with this first and last name already exists in the facility
        if not self.cleaned_data.get("warned", False) and (self.cleaned_data["first_name"] or self.cleaned_data["last_name"]):
            users_with_same_name = FacilityUser.objects.filter(first_name__iexact=self.cleaned_data["first_name"], last_name__iexact=self.cleaned_data["last_name"]) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same facility
            if users_with_same_name and (not self.instance or self.instance not in users_with_same_name):
                self.data = copy.deepcopy(self.data)
                self.data["warned"] = self.cleaned_data["warned"] = True
                msg = "%s %s" % (_("%(num_users)d user(s) with first name '%(f_name)s' and last name '%(l_name)s' already exist(s).") % {
                    "num_users": users_with_same_name.count(),
                    "f_name": self.cleaned_data["first_name"],
                    "l_name": self.cleaned_data["last_name"],
                }, _("If you are sure you want to create this user, you may re-submit the form to complete the process."))
                self.set_field_error(message=msg)  # general error, not associated with a field.

        if self.has_errors():
            return self.cleaned_data
        else:
            return super(FacilityUserForm, self).clean()
Exemple #4
0
    def clean(self):
        facility = self.cleaned_data.get('facility')
        username = self.cleaned_data.get('username', '')
        zone = self.cleaned_data.get('zone_fallback')

        ## check if given username is unique on both facility users and admins, whatever the casing
        #
        # Change: don't allow (only through the form) the same username either in the same facility,
        #   or even in the same zone.
        # Change: Use 'all_objects' instead of 'objects' in order to return soft deleted users as well.
        users_with_same_username = FacilityUser.all_objects.filter(username__iexact=username, facility=facility) \
            or FacilityUser.all_objects.filter(username__iexact=username) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same zone
        username_taken = users_with_same_username.count() > 0
        username_changed = not self.instance or self.instance.username != username
        if username_taken and username_changed:
            error_message = _("A user with this username already exists. Please choose a new username and try again.")
            self.set_field_error(field_name='username', message=error_message)

        elif User.objects.filter(username__iexact=username).count() > 0:
            # Admin (django) user exists with the same name; we don't want overlap there!
            self.set_field_error(field_name='username', message=_("The specified username is unavailable. Please choose a new username and try again."))

        ## Check password
        password_first = self.cleaned_data.get('password_first', "")
        password_recheck = self.cleaned_data.get('password_recheck', "")
        # If they have put anything in the new password field, it must match the password check field
        if password_first != password_recheck:
            self.set_field_error(field_name='password_recheck', message=_("The passwords didn't match. Please re-enter the passwords."))
        
        # Next, enforce length if they submitted a password
        if password_first:
            try:
                verify_raw_password(password_first)
            except ValidationError as ve:
                self.set_field_error(field_name='password_first', message=ve.messages[0])

        ## Warn the user during sign up or adding user if a user with this first and last name already exists in the facility
        if not self.cleaned_data.get("warned", False) and (self.cleaned_data["first_name"] or self.cleaned_data["last_name"]):
            users_with_same_name = FacilityUser.objects.filter(first_name__iexact=self.cleaned_data["first_name"], last_name__iexact=self.cleaned_data["last_name"]) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same facility
            if users_with_same_name and (not self.instance or self.instance not in users_with_same_name):
                self.data = copy.deepcopy(self.data)
                self.data["warned"] = self.cleaned_data["warned"] = True
                msg = "%s %s" % (_("%(num_users)d user(s) with first name '%(f_name)s' and last name '%(l_name)s' already exist(s).") % {
                    "num_users": users_with_same_name.count(),
                    "f_name": self.cleaned_data["first_name"],
                    "l_name": self.cleaned_data["last_name"],
                }, _("If you are sure you want to create this user, you may re-submit the form to complete the process."))
                self.set_field_error(message=msg)  # general error, not associated with a field.

        if self.has_errors():
            return self.cleaned_data
        else:
            return super(FacilityUserForm, self).clean()
Exemple #5
0
    def clean(self):
        facility = self.cleaned_data.get('facility')
        username = self.cleaned_data.get('username', '')
        zone = self.cleaned_data.get('zone_fallback')

        ## check if given username is unique on both facility users and admins, whatever the casing
        #
        # Change: don't allow (only through the form) the same username either in the same facility,
        #   or even in the same zone.
        users_with_same_username = FacilityUser.objects.filter(username__iexact=username, facility=facility) \
            or FacilityUser.objects.filter(username__iexact=username) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same zone
        username_taken = users_with_same_username.count() > 0
        username_changed = not self.instance or self.instance.username != username
        if username_taken and username_changed:
            error_message = _("A user with this username already exists. Please choose a new username and try again.")
            self.set_field_error(field_name='username', message=error_message)

        elif User.objects.filter(username__iexact=username).count() > 0:
            # Admin (django) user exists with the same name; we don't want overlap there!
            self.set_field_error(field_name='username', message=_("The specified username is unavailable. Please choose a new username and try again."))

        ## Check password
        password_first = self.cleaned_data.get('password_first', "")
        password_recheck = self.cleaned_data.get('password_recheck', "")
        # If they have put anything in the new password field, it must match the password check field
        if password_first != password_recheck:
            self.set_field_error(field_name='password_recheck', message=_("The passwords didn't match. Please re-enter the passwords."))
        
        # Next, enforce length if they submitted a password
        if password_first:
            try:
                verify_raw_password(password_first)
            except ValidationError as ve:
                self.set_field_error(field_name='password_first', message=ve.messages[0])

        ## Warn the user during sign up or adding user if a user with this first and last name already exists in the faiclity
        if not self.cleaned_data.get("warned", False) and (self.cleaned_data["first_name"] or self.cleaned_data["last_name"]):
            users_with_same_name = FacilityUser.objects.filter(first_name__iexact=self.cleaned_data["first_name"], last_name__iexact=self.cleaned_data["last_name"]) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same facility
            if users_with_same_name and (not self.instance or self.instance not in users_with_same_name):
                self.data = copy.deepcopy(self.data)
                self.data["warned"] = self.cleaned_data["warned"] = True
                msg = "%s %s" % (_("%(num_users)d user(s) with first name '%(f_name)s' and last name '%(l_name)s' already exist(s).") % {
                    "num_users": users_with_same_name.count(),
                    "f_name": self.cleaned_data["first_name"],
                    "l_name": self.cleaned_data["last_name"],
                }, _("If you are sure you want to create this user, you may re-submit the form to complete the process."))
                self.set_field_error(message=msg)  # general error, not associated with a field.

        if self.has_errors():
            return self.cleaned_data
        else:
            return super(FacilityUserForm, self).clean()
    def handle(self, *args, **options):
        if len(args) != 1:
            raise CommandError("need exactly one argument (username)")

        if args:
            username, = args

        try:
            u = FacilityUser.objects.using(options.get('database')).get(username=username)
        except FacilityUser.DoesNotExist:
            raise CommandError("user '%s' does not exist" % username)

        self.stdout.write("Changing password for user '%s'\n" % u.username)

        if options['noinput']:
            p1 = generate_random_password()
            self.stdout.write("Generated new password for user '%s': '%s'\n" % (username, p1))

        else:
            MAX_TRIES = 3
            count = 0
            p1, p2 = 1, 2  # To make them initially mismatch.
            while p1 != p2 and count < MAX_TRIES:
                p1 = self._get_pass()
                try:
                    verify_raw_password(p1)
                except ValidationError as e:
                    self.stderr.write(unicode(e) + "\n")
                    count += 1
                    continue
                p2 = self._get_pass("Password (again): ")
                if p1 != p2:
                    self.stdout.write("Passwords do not match. Please try again.\n")
                    count = count + 1

            if count == MAX_TRIES:
                raise CommandError("Aborting password change for user '%s' after %s attempts" % (username, count))

        u.set_password(p1)
        u.save()

        return "Password changed successfully for user '%s'\n" % u.username
Exemple #7
0
    def clean(self):

        facility = self.cleaned_data.get('facility')
        username = self.cleaned_data.get('username', '')
        zone = self.cleaned_data.get('zone_fallback')

        ## check if given username is unique on both facility users and admins, whatever the casing
        #
        # Change: don't allow (only through the form) the same username either in the same facility,
        #   or even in the same zone.
        users_with_same_username = FacilityUser.objects.filter(username__iexact=username, facility=facility) \
            or FacilityUser.objects.filter(username__iexact=username) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same zone
        username_taken = users_with_same_username.count() > 0
        username_changed = not self.instance or self.instance.username != username
        if username_taken and username_changed:
            error_message = _(
                "A user with this username already exists. Please choose a new username and try again."
            )
            self.set_field_error(field_name='username', message=error_message)

        elif User.objects.filter(username__iexact=username).count() > 0:
            # Admin (django) user exists with the same name; we don't want overlap there!
            self.set_field_error(
                field_name='username',
                message=
                _("The specified username is unavailable. Please choose a new username and try again."
                  ))

        ## Check password
        password_first = self.cleaned_data.get('password_first', "")
        password_recheck = self.cleaned_data.get('password_recheck', "")
        if (self.instance and not self.instance.password) or password_first:
            # No password set, or password is being reset
            try:
                verify_raw_password(password_first)
            except ValidationError as ve:
                self.set_field_error(field_name='password_first',
                                     message=ve.messages[0])
        elif (self.instance and not self.instance.password
              ) or password_first or password_recheck:
            # Only perform check on a new user or a password change
            if password_first != password_recheck:
                self.set_field_error(
                    field_name='password_recheck',
                    message=
                    _("The passwords didn't match. Please re-enter the passwords."
                      ))

        ## Check the name combo; do it here so it's a general error.
        if not self.cleaned_data.get("warned", False):
            users_with_same_name = FacilityUser.objects.filter(first_name__iexact=self.cleaned_data["first_name"], last_name__iexact=self.cleaned_data["last_name"]) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same facility
            if users_with_same_name and (not self.instance or self.instance
                                         not in users_with_same_name):
                self.data = copy.deepcopy(self.data)
                self.data["warned"] = self.cleaned_data["warned"] = True
                msg = "%s %s" % (
                    _("%(num_users)d user(s) with this name already exist(s)%(username_list)s."
                      ) %
                    {
                        "num_users":
                        users_with_same_name.count(),
                        "username_list":
                        "" if not self.admin_access else " " + str([
                            user["username"]
                            for user in users_with_same_name.values("username")
                        ]),
                    },
                    _("Please consider choosing another name, or re-submit to complete."
                      ))
                self.set_field_error(
                    message=msg)  # general error, not associated with a field.

        if self.has_errors():
            return self.cleaned_data
        else:
            return super(FacilityUserForm, self).clean()
Exemple #8
0
    def clean(self):
        facility = self.cleaned_data.get('facility')
        username = self.cleaned_data.get('username', '')
        zone = self.cleaned_data.get('zone_fallback')

        # Don't allow (only through the form) the same username within the same facility, or conflicting with the admin.
        users_with_same_username = FacilityUser.objects.filter(
            username__iexact=username, facility=facility)
        username_taken = users_with_same_username.count() > 0
        username_changed = not self.instance or self.instance.username != username
        if username_taken and username_changed or User.objects.filter(
                username__iexact=username).count() > 0:
            self.set_field_error(
                field_name='username',
                message=
                _("A user with this username already exists. Please choose a new username and try again."
                  ))

        ## Check password
        password_first = self.cleaned_data.get('password_first', "")
        password_recheck = self.cleaned_data.get('password_recheck', "")
        # If they have put anything in the new password field, it must match the password check field
        if password_first != password_recheck:
            self.set_field_error(
                field_name='password_recheck',
                message=_(
                    "The passwords didn't match. Please re-enter the passwords."
                ))

        # Next, enforce length if they submitted a password
        if password_first:
            try:
                verify_raw_password(password_first)
            except ValidationError as ve:
                # MUST: The ValidationError constructor sets the error message into a list with
                # `self.messages = [message]` so we get the first message from the list.  It
                # should have assigned the value to `self.message = message` too but maybe on
                # newer Django versions this is fixed.
                message = ''
                if hasattr(ve, 'messages') and isinstance(
                        ve.messages, list) and ve.messages:
                    message = ve.messages[0]
                self.set_field_error(field_name='password_first',
                                     message=message)

        elif (self.instance and not self.instance.password
              ) or password_first or password_recheck:
            # Only perform check on a new user or a password change
            if password_first != password_recheck:
                self.set_field_error(
                    field_name='password_recheck',
                    message=
                    _("The passwords didn't match. Please re-enter the passwords."
                      ))

        ## Warn the user during sign up or adding user if a user with this first and last name already exists in the facility
        if not self.cleaned_data.get(
                "warned", False) and (self.cleaned_data["first_name"]
                                      or self.cleaned_data["last_name"]):
            users_with_same_name = FacilityUser.objects.filter(first_name__iexact=self.cleaned_data["first_name"], last_name__iexact=self.cleaned_data["last_name"]) \
                .filter(Q(signed_by__devicezone__zone=zone) | Q(zone_fallback=zone))  # within the same facility
            if users_with_same_name and (not self.instance or self.instance
                                         not in users_with_same_name):
                self.data = copy.deepcopy(self.data)
                self.data["warned"] = self.cleaned_data["warned"] = True
                msg = "%s %s" % (
                    _("%(num_users)d user(s) with first name '%(f_name)s' and last name '%(l_name)s' already exist(s)."
                      ) % {
                          "num_users": users_with_same_name.count(),
                          "f_name": self.cleaned_data["first_name"],
                          "l_name": self.cleaned_data["last_name"],
                      },
                    _("If you are sure you want to create this user, you may re-submit the form to complete the process."
                      ))
                self.set_field_error(
                    message=msg)  # general error, not associated with a field.

        if self.has_errors():
            return self.cleaned_data
        else:
            return super(FacilityUserForm, self).clean()