Django:如何在添加模型对象到数据库前进行操作?

1 投票
4 回答
890 浏览
提问于 2025-04-16 09:57

在Python-Django中,我有一个模型,这个模型里面有一个文件字段,用来存储视频文件。

我想要“干预”Django标准的“添加模型行/对象/实例”的过程,在把每个视频真正添加到数据库之前,先对它进行一些处理。

这个处理就是把视频转换成一种统一的格式。这样,所有添加的视频最终都会以同样的格式存储(WebM)。

我该怎么做呢?我查过Django的自定义管理器,但我觉得那不是我需要的。

谢谢。:)

4 个回答

3

你也可以使用 django信号 来触发一些事件,比如在数据要保存到数据库之前或之后。

具体来说,你可以用 Signal.connect() 方法来连接你想要启动的信号处理器,比如 pre_save(保存前)、post_save(保存后)、pre_delete(删除前)、post_delete(删除后)等等。

为了设置这些,你需要做以下步骤:

signals.py:

from django.db.models.signals import *

def entry_action_post_save(sender, instance, **kwargs):
    # what do we want to do here?
    pass

post_save.connect    (entry_action_post_save,        sender=Entry)

在这里,Entry 是一个从 models.Model 继承的类。

这个博客还介绍了一种替代的方法,可以在 models.py 中使用调度器 来设置。

需要注意的是,由于你在考虑视频编码,可能不想在这些方法里实际重新编码视频,否则你的请求会花费很长时间才能完成。更好的方法是检查编码,并让模型有一个 status 字段来表示 webMnotwebm。然后把编码的任务交给其他地方处理,直到完成之前,不要显示视频(Videos.objects.filter(format='webm')。

5

你可以选择重写 save() 方法,或者使用 信号

不过,转换视频会花费很多时间。在你的网页请求中同步进行这个操作可能不是个好主意。一个常见的做法是把这个工作放到一个任务队列里去处理。可以看看 Celery,它就是用来做这个的。

3

我其实正在做同样的事情。你不想在接收视频文件的同时就处理它,原因有几个:

1) 这样会让用户在一个没有反应的页面上等待很长时间,可能会导致超时,他们会怀疑这个操作是否成功。

2) 如果他们去查看上传的状态,而这个过程还没有完成并且没有保存到数据库(数据不一致),他们会觉得系统出问题了。

你应该先在服务器上保存记录和文件,并标记为“需要处理”。然后启动一个celery任务来处理这些工作,完成后再更新这个标记。我现在正在用zencoder做这个项目,效果很好。

Celery: http://pypi.python.org/pypi/django-celery
Ghettoq(本地使用): http://pypi.python.org/pypi/ghettoq

撰写回答