Django Admin:修改用户状态时无需更新密码
解决Django自定义用户模型Admin修改状态需输入密码的问题
问题根源
Django自带的UserAdmin类是针对默认用户模型设计的,它的修改表单会默认将密码字段设为必填项。当自定义用户模型直接继承UserAdmin时,会保留这一逻辑,导致修改用户非密码字段(如is_staff)时,也被强制要求输入密码。
解决方案
需要自定义Admin类,调整修改用户时的表单逻辑,分离密码修改与常规字段修改的流程:
方法1:自定义修改表单,移除密码字段的必填要求
在项目的admin.py中,创建自定义的用户修改表单,再关联到自定义的UserAdmin类中:
from django.contrib import admin from django.contrib.auth.admin import UserAdmin from django.contrib.auth.forms import UserChangeForm from .models import CustomUser # 替换为你的自定义用户模型 class CustomUserChangeForm(UserChangeForm): class Meta(UserChangeForm.Meta): model = CustomUser def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) # 将密码字段设为非必填 self.fields['password'].required = False # 若想彻底隐藏密码字段,可使用:del self.fields['password'] class CustomUserAdmin(UserAdmin): form = CustomUserChangeForm # 根据自定义模型调整字段配置,确保is_staff等权限字段可见 fieldsets = ( (None, {'fields': ('username', 'password')}), ('权限设置', {'fields': ('is_active', 'is_staff', 'is_superuser', 'groups', 'user_permissions')}), ('关键日期', {'fields': ('last_login', 'date_joined')}), # 此处添加你的自定义用户字段(如果有) ) admin.site.register(CustomUser, CustomUserAdmin)
方法2:分离密码修改逻辑,常规修改页不显示密码字段
利用Django内置的密码修改页面入口,在常规用户修改表单中隐藏密码字段,仅保留专门的密码修改通道:
from django.contrib import admin from django.contrib.auth.admin import UserAdmin from .models import CustomUser class CustomUserAdmin(UserAdmin): # 常规修改页面不显示密码字段 fieldsets = ( (None, {'fields': ('username',)}), ('权限设置', {'fields': ('is_active', 'is_staff', 'is_superuser', 'groups', 'user_permissions')}), ('关键日期', {'fields': ('last_login', 'date_joined')}), # 此处添加你的自定义用户字段(如果有) ) # 保留新增用户时的密码设置表单 add_fieldsets = ( (None, { 'classes': ('wide',), 'fields': ('username', 'password1', 'password2', 'is_staff'), }), ) admin.site.register(CustomUser, CustomUserAdmin)
配置完成后,修改用户权限等信息时不会出现密码字段,如需修改密码,可通过用户详情页的「Change password」按钮进入专门页面操作。
注意事项
- 若自定义用户模型继承的是
AbstractBaseUser而非AbstractUser,需确保Admin类正确配置标识字段(如username),避免出现异常。 - 务必根据自身自定义模型的字段,调整
fieldsets、list_display等Admin配置项,保证需要修改的字段正常显示。
内容的提问来源于stack exchange,提问作者Zohaib Durrani
相关产品推荐
相关产品推荐

