You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Django中为普通用户与管理员用户设置独立字段?

实现普通用户与管理员的字段区分方案

推荐方案:基础用户模型 + 普通用户关联Profile(Django官方推荐)

这种方式通过一对一关联给普通用户扩展字段,既保留共同字段的统一存储,又实现普通用户的额外字段需求,避免单表冗余。

1. 定义基础自定义用户模型

基于AbstractUser扩展,将email设为登录标识,包含所有用户的共同字段:

from django.contrib.auth.models import AbstractUser
from django.db import models

class CustomUser(AbstractUser):
    # 移除默认username,用email作为唯一登录字段
    username = None
    email = models.EmailField(unique=True)
    # first_name、last_name为AbstractUser自带字段,无需重复定义(如需修改参数可重写)

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['first_name', 'last_name']

    class Meta:
        verbose_name = '用户'
        verbose_name_plural = '用户'

2. 创建普通用户专属扩展模型

通过OneToOneField关联基础用户模型,添加普通用户需要的额外字段:

class UserProfile(models.Model):
    user = models.OneToOneField(CustomUser, on_delete=models.CASCADE, related_name='profile')
    # 示例额外字段,可根据需求修改
    phone_number = models.CharField(max_length=20, blank=True)
    address = models.TextField(blank=True)
    date_of_birth = models.DateField(null=True, blank=True)

    def __str__(self):
        return f"{self.user.email} 的个人信息"

3. 配置项目settings

在settings.py中指定自定义用户模型:

AUTH_USER_MODEL = '你的应用名.CustomUser'

4. 执行数据迁移

生成并应用迁移文件,创建两张独立的表(基础用户表+普通用户扩展表):

python manage.py makemigrations
python manage.py migrate

可选:自动为普通用户创建Profile

通过信号实现新用户创建时,自动为非管理员生成Profile记录:

# 在应用的signals.py文件中编写
from django.db.models.signals import post_save
from django.dispatch import receiver
from .models import CustomUser, UserProfile

@receiver(post_save, sender=CustomUser)
def create_regular_user_profile(sender, instance, created, **kwargs):
    if created and not instance.is_staff:
        UserProfile.objects.create(user=instance)

@receiver(post_save, sender=CustomUser)
def save_regular_user_profile(sender, instance, **kwargs):
    if hasattr(instance, 'profile'):
        instance.profile.save()

然后在应用的apps.py中注册信号:

from django.apps import AppConfig

class YourAppConfig(AppConfig):
    default_auto_field = 'django.db.models.BigAutoField'
    name = '你的应用名'

    def ready(self):
        import 你的应用名.signals

不推荐方案:多表继承

若坚持用多表继承实现,需定义抽象基础模型,再分别创建管理员和普通用户模型,但此方式会增加查询复杂度,且Django仅支持指定一个AUTH_USER_MODEL,需额外处理认证逻辑,不推荐用于生产环境:

from django.contrib.auth.models import AbstractBaseUser, BaseUserManager, PermissionsMixin
from django.db import models

# 抽象基础模型,不生成实际表
class BaseUser(AbstractBaseUser, PermissionsMixin):
    email = models.EmailField(unique=True)
    first_name = models.CharField(max_length=100)
    last_name = models.CharField(max_length=100)
    is_active = models.BooleanField(default=True)
    is_staff = models.BooleanField(default=False)

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['first_name', 'last_name']

    objects = BaseUserManager()

    class Meta:
        abstract = True

# 管理员用户模型
class AdminUser(BaseUser):
    class Meta:
        verbose_name = '管理员'

# 普通用户模型,添加额外字段
class RegularUser(BaseUser):
    phone_number = models.CharField(max_length=20, blank=True)
    address = models.TextField(blank=True)

    class Meta:
        verbose_name = '普通用户'

内容的提问来源于stack exchange,提问作者Achira Silva

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 12:42:57