Question

I have two related (via foreignkey relation) models and created admin model for parent with inlines. In several cases (edited in admin by boolean field), i need to delete all previous objects (inlines) and create new ones. I've tried to make it with save_model, where i can get all current object's properties and decide if i need to recreate (inline) objects. models:

class Model1(models.Model):
    reformat = models.BooleanField(default=False)
    ...
class Model2(models.Model):
    model1 = ForeignKey(Model1, related_name='model2')
    ...

admin:

class Model2Inline(admin.TabularInline):
    model = Model2

class Model1Admin(admin.ModelAdmin):
    inlines = [Model2Inline]
    def save_model(self, request, obj, form, change):
        super(Model1Admin, self).save_model(request, obj, form, change)
        if obj.reformat:
            obj.model2.all().delete()
            # creating new objects
            ...
        obj.save()

But if i try to delete these objects in model_save method i get ValidationError. Is there other possibilities to solve this problem?

Was it helpful?

Solution

I came across this problem as well, and, after an hour or two of banging my head against the wall, solved it by overriding save_formset() on the admin object instead of save_model() and doing the required manipulation after calling the super class's save_formset() method. Doing it this way means the models which you are deleting are still present when the formset is saved, so you don't get the validation error.

Here's what it might look like in the example you gave:

class Model2Inline(admin.TabularInline):
    model = Model2

class Model1Admin(admin.ModelAdmin):
    inlines = [Model2Inline]
    def save_formset(self, request, form, formset, change):
        super(Model1Admin, self).save_formset(request, form, formset, change)
        if formset.model is Model2:
            obj = formset.instance
            if obj.reformat:
                obj.model2.all().delete()
                # creating new objects
                ...
            obj.save()
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top