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

如何为Django模型添加created_by和modified_by字段?

实现步骤

1. 为LockData模型添加字段

首先在sample/models.py中导入django.conf.settings,然后在LockData类中添加两个关联自定义用户模型的外键字段:

from django.conf import settings
from django.db import models
# 保留原有的其他导入...

class LockData(models.Model):
    patient=models.ForeignKey(Patient, on_delete=CASCADE, default=None)
    patient_type=models.ForeignKey(PatientType, on_delete=CASCADE, default=None, blank=True, null=True)
    lock=models.BooleanField(default=False)
    date=models.DateField(default=datetime.date.today)
    created_on=models.DateTimeField(auto_now_add=True)
    modified_on=models.DateTimeField(auto_now=True)
    # 新增created_by和modified_by字段
    created_by = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
        related_name='lockdata_created'
    )
    modified_by = models.ForeignKey(
        settings.AUTH_USER_MODEL,
        on_delete=models.SET_NULL,
        null=True,
        blank=True,
        related_name='lockdata_modified'
    )
  • 使用settings.AUTH_USER_MODEL是Django推荐的关联自定义用户模型的方式,避免硬编码依赖。
  • on_delete=models.SET_NULL表示当关联用户被删除时,字段值设为null,你可根据业务需求改为PROTECT(禁止删除关联用户)等其他选项。
  • related_name用于反向查询,方便从用户实例快速查找其创建/修改的LockData记录。

2. 自动填充字段值

有两种实用方式实现自动赋值,任选其一即可:

方式一:重写模型save方法(需在视图传递用户)

如果视图中能直接获取当前登录用户,可重写save方法接收用户参数,自动赋值:

class LockData(models.Model):
    # 保留原字段定义...

    def save(self, *args, user=None, **kwargs):
        if user and not self.pk:  # 新建记录时设置created_by
            self.created_by = user
        if user:  # 每次保存都更新modified_by
            self.modified_by = user
        super().save(*args, **kwargs)

在视图中保存实例时,传入当前用户:

# 示例:在类视图的post方法中
def post(self, request):
    form = LockDataForm(request.POST)
    if form.is_valid():
        lock_data = form.save(commit=False)
        lock_data.save(user=request.user)
        # 其他业务逻辑...

方式二:使用Django信号+线程本地存储(全自动)

这种方式无需在视图中手动传递用户,通过中间件存储当前用户,再用信号自动赋值:

步骤2.1:创建中间件存储当前用户

在项目根目录下新建middleware.py,添加以下代码:

import threading
from django.utils.deprecation import MiddlewareMixin

_thread_locals = threading.local()

def get_current_user():
    return getattr(_thread_locals, 'user', None)

class CurrentUserMiddleware(MiddlewareMixin):
    def process_request(self, request):
        _thread_locals.user = request.user if request.user.is_authenticated else None

然后在settings.py的MIDDLEWARE列表中注册该中间件:

MIDDLEWARE = [
    # 保留原有中间件...
    '你的项目名称.middleware.CurrentUserMiddleware',
]

步骤2.2:编写信号处理函数

在sample/models.py末尾添加信号逻辑:

from django.db.models.signals import pre_save
from django.dispatch import receiver
from .middleware import get_current_user

@receiver(pre_save, sender=LockData)
def set_user_fields(sender, instance, **kwargs):
    user = get_current_user()
    if user:
        if not instance.pk:  # 新建记录时赋值created_by
            instance.created_by = user
        instance.modified_by = user  # 每次保存都更新modified_by

这样无论在何处保存LockData实例,只要当前有登录用户,字段都会自动赋值。

3. 执行数据库迁移

添加字段后,运行以下命令完成数据库更新:

python manage.py makemigrations
python manage.py migrate

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.09 20:30:27