Django的。 覆盖保存模型

保存模型之前,我正在重新设置图片大小。 但是我怎样才能检查新图片是否添加或只是描述更新,所以我可以跳过每次模型保存时重新缩放?

class Model(model.Model): image=models.ImageField(upload_to='folder') thumb=models.ImageField(upload_to='folder') description=models.CharField() def save(self, *args, **kwargs): if self.image: small=rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) super(Model, self).save(*args, **kwargs) 

我只想在新图像加载或图像更新时重新resize,而不是在更新描述时resize。

一些想法:

 class Model(model.Model): _image=models.ImageField(upload_to='folder') thumb=models.ImageField(upload_to='folder') description=models.CharField() def set_image(self, val): self._image = val self._image_changed = True # Or put whole logic in here small = rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) def get_image(self): return self._image image = property(get_image, set_image) # this is not needed if small_image is created at set_image def save(self, *args, **kwargs): if getattr(self, '_image_changed', True): small=rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) super(Model, self).save(*args, **kwargs) 

不知道它是否会与所有伪自动django工具(例如:ModelForm,contrib.admin等)很好玩。

检查模型的PK字段。 如果是None,那么这是一个新的对象。

 class Model(model.Model): image=models.ImageField(upload_to='folder') thumb=models.ImageField(upload_to='folder') description=models.CharField() def save(self, *args, **kwargs): if 'form' in kwargs: form=kwargs['form'] else: form=None if self.pk is None and form is not None and 'image' in form.changed_data: small=rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) super(Model, self).save(*args, **kwargs) 

编辑:我已经在form.changed_data添加了一个检查“图像”。 这假设您正在使用pipe理网站来更新您的图片。 您还必须覆盖默认的save_model方法,如下所示。

 class ModelAdmin(admin.ModelAdmin): def save_model(self, request, obj, form, change): obj.save(form=form) 

您可以提供额外的参数来确认发布新图像。
就像是:

 def save(self, new_image=False, *args, **kwargs): if new_image: small=rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) super(Model, self).save(*args, **kwargs) 

或传递请求variables

 def save(self, request=False, *args, **kwargs): if request and request.FILES.get('image',False): small=rescale_image(self.image,width=100,height=100) self.image_small=SimpleUploadedFile(name,small_pic) super(Model, self).save(*args, **kwargs) 

我认为这些不会打破你的保存时简单地调用。

你可以把这个放在你的admin.py中,这样也可以在pipe理员站点上使用(对于以上解决scheme中的第二个):

 class ModelAdmin(admin.ModelAdmin): .... def save_model(self, request, obj, form, change): instance = form.save(commit=False) instance.save(request=request) return instance 

我做了什么来实现这个目标是做这个..

 # I added an extra_command argument that defaults to blank def save(self, extra_command="", *args, **kwargs): 

和下面的save()方法是..

 # override the save method to create an image thumbnail if self.image and extra_command != "skip creating photo thumbnail": # your logic here 

所以当我编辑一些领域,但不编辑图像,我把这个..

 Model.save("skip creating photo thumbnail") 

您可以将"skip creating photo thumbnail"replace为"im just editing the description"或更正式的文本。

希望这个帮助!

用相同的PK查询数据库中现有的logging。 比较新图像和现有图像的文件大小和校验和,看它们是否相同。

在新版本中是这样的:

 def validate(self, attrs): has_unknown_fields = set(self.initial_data) - set(self.fields.keys()) if has_unknown_fields: raise serializers.ValidationError("Do not send extra fields") return attrs