Позволете на потребители, които не са суперадминистратори, да нулират паролата за друг потребител в django admin

Работя върху приложение на трета страна, работещо с django 2.2.12.

Имам администратор с 3 вида потребители: "superadmin", "personal" и "other".

Когато съм влязъл като "superadmin", когато отида в списъка с потребители и щракна върху потребител, мога да го редактирам и да нулирам паролата му.

Въпреки това, когато се опитам да направя същото като потребител от „персонал“, мога да видя потребителските данни, но не мога да редактирам нищо и няма опция за повторно задаване на паролата. Ако се опитам да осъществя достъп до URL адреса ръчно (/admin/accounts/user/[USER_ID]/password/), получавам съобщение за грешка „403 Forbidden“.

Забелязах, че ако отменя метода has_perm в потребителския модел, това позволява на потребителя "персонал" да редактира потребителските данни. Въпреки това бих искал да разреша само промяната на паролата (ако потребителят не е суперадминистратор или потребител от персонала), без да позволявам на потребителите от персонала да редактират други потребители.

def has_perm(self, perm, obj=None):
    return True

Имам впечатлението, че това е свързано със системата за разрешения на Django, но прочетох отново документите на https://docs.djangoproject.com/en/2.2/topics/auth/default/ и все още не можах да разбера това.

Благодаря


person ThiagoAlves    schedule 21.04.2020    source източник
comment
Мисля, че ще ви трябва използването на пакет Вижте този отговор   -  person Shubham Yadav    schedule 21.04.2020
comment
@ShubhamYadav Благодаря. Ще разгледам Възможно ли е програмно да се позволи на потребителите от персонала да редактират Потребителите, но да се скрият всички негови свойства, с изключение на паролата? Вярвам, че това решение ще реши проблема.   -  person ThiagoAlves    schedule 21.04.2020


Отговори (1)


Добре, успях да го накарам да работи с не толкова идеално решение, но успях.

По принцип претоварвам метода has_change_permission на класа UserAdmin и добавям персонализирана логика, за да позволя промяната на паролата в специален случай (url завършва с '/password' и потребителят има правилните разрешения.

    def can_edit_password(self, logged_user, chosen_user=None):
        if logged_user and logged_user.is_superuser:
            return True

        logged_user_has_change_pass_perm = (
            logged_user and
            logged_user.is_authenticated and
            logged_user.has_perm("accounts.change_student_password")
        )
        return logged_user_has_change_pass_perm

    def can_show_change_password_form(self, path, logged_user, chosen_user=None):
        is_changing_password = path.endswith('/password/')
        return is_changing_password and self.can_edit_password(logged_user, chosen_user)

    def has_change_permission(self, request, user=None):
        if self.can_show_change_password_form(path=request.path, logged_user=request.user, chosen_user=user):
            return True
        return super(UserAdmin, self).has_change_permission(request, user)
person ThiagoAlves    schedule 22.04.2020