Amir Afianian
Amir Afianian

Reputation: 2795

django: calling delete on object doesn't delete the file

So I have the following model.

class StoreSegments01(models.Model):
    segment = models.FileField(upload_to=content_file_name)
    segmentID = models.TextField(max_length=100, default=11)

class StoreSegments01Form(forms.ModelForm):
    class Meta:
    model = StoreSegments01
    fields = ['segment', 'segmentID']

def content_file_name(instance, filename):
    return '{0}'.format(instance.segmentID)

I want to provide a way for the users to delete their files. In manage.py shell I try the following:

obj = StoreSegments01.objects.get(segmentID='239fd363-562a-41b3-a915-b7a84cc4a172')
>>> obj.delete()

It deletes the record related to the specified segmentID, but the file associated with the ID is still there. I tried the same with queryset, still the file is not deleted.

What am I missing here?

Upvotes: 4

Views: 3161

Answers (1)

xyres
xyres

Reputation: 21754

Here's an alternative to using signals: override the delete method of your model.

Example:

class StoreSegments01(models.Model):
    segment = models.FileField(upload_to=content_file_name)
    segmentID = models.TextField(max_length=100, default=11)

    def delete(self, *args, **kwargs):
        # first, delete the file
        self.segment.delete(save=False)

        # now, delete the object
        super(StoreSegments01, self).delete(*args, **kwargs)

For Python 3, call super like this: super().delete(*args, **kwargs)

Heads up! : This works if you delete individual objects. But if you delete objects in bulk, the associated files aren't deleted. Because deleting a single object calls model.delete() method but deleting in bulk calls queryset.delete() method. Thanks to Håken Lid who pointed this out in a comment below.

Upvotes: 4

Related Questions