如何在 django 中为 sorl-thumbnail 设计清理任务?
Posted
技术标签:
【中文标题】如何在 django 中为 sorl-thumbnail 设计清理任务?【英文标题】:How to design cleanup tasks for sorl-thumbnail in django? 【发布时间】:2013-12-26 07:30:02 【问题描述】:我正在使用 sorl-thumbnail,它提供给定图像的缓存缩略图。 我想在原始图像更改或被删除时删除生成的拇指。 我知道 sorl-thumbnail 为这种情况提供了删除方法,但是..
不会通过 django-admin 触发 可能是争用条件的坏原因 当使用像 redis 这样的 kv 存储时 - 所有数据(文件连接)都可能消失(例如重新启动)更适合的是 sorl cleanup 管理命令。此命令将删除原始链接断开的 kv 条目和相关的物理拇指。但是如果我的kv存储不完整怎么办?我不想到处乱扔死文件。
我想到了一个 celery 任务,它会触发清理命令并另外检查所有缓存的文件,但不知道如何设计。
检测和清理这些混乱的最佳方法是什么?
【问题讨论】:
【参考方案1】:您可以向模型添加方法 clear_thumbnails()。在 clear_thumbnails() 中,您使用 sorl-thumbnail 中的 delete function 删除现有缩略图。如果下次使用% thumbnail %
模板标签渲染视图,则会创建新的缩略图。
现在您添加一个函数,该函数在调用与缩略图相关的模型的pre_save signal 时运行。在此函数中,您只需调用 clear_thumbnails()
使用这种方法,当您在 Django admin 中更改模型时,缩略图也会被删除。 (你也可以捕捉到 pre_delete 信号)
类似这样的:
## models.py ##
from django.db import models
from sorl.thumbnail import delete as delete_thumbnails
class Route(models.Model):
...
def clear_thumbnails(self):
delete_thumbnails(self.image)
## receivers.py ##
from django.db.models.signals import pre_save
@receiver(pre_save, sender=YourModel)
def receive_yourmodel_pre_save(sender, **kwargs):
sender.clear_thumbnails()
现在您有了一个模型,该模型可以在模型更改时删除缩略图。 (如果图像字段发生更改,则如果 pre_save 或 post_save 信号,也许您应该在接收器中添加检查,并且仅在发生这种情况时删除缩略图)
如果你有很多缩略图,那么 sorl-thumbnails 的管理命令就没用了。我在 sorl-thumbnails 键值存储中有几百万个条目,并且管理命令永远不会完成。
我最终编写了自己的小清理脚本,它比 sorl-thumbnails 提供的更好,因为它不使用太多内存并且还显示了一个进步。像这样的:
function clean_thumbnails(self):
max_id = MyModel.objects.all().order_by('-pk')[0].pk
for id in xrange(max_id, 0, -1):
try:
my_obj = MyModel.objects.get(pk=id)
my_obj.clear_thumbnails()
print "processed object with id %s" % id
except MyModel.DoesNotExist:
pass
我将此清理脚本设置为RunScript as defined the Django extensions。查看 Django 扩展和 RunScript 部分。这很方便。
希望这会有所帮助。
【讨论】:
以上是关于如何在 django 中为 sorl-thumbnail 设计清理任务?的主要内容,如果未能解决你的问题,请参考以下文章