这个问题可能看起来类似于this one,但是不是...
我有一个像这样的模型结构:
class Customer(models.Model):
....
class CustomerCompany(models.Model):
customer = models.ForeignKey(Customer)
type = models.SmallIntegerField(....)
我正在使用
InlineModels
,并且有两种类型的CustomerCampany.type
。所以我为CustomerCompany
和ov over InlineModelAdmin.queryset
定义了两个不同的内联class CustomerAdmin(admin.ModelAdmin):
inlines=[CustomerCompanyType1Inline, CustomerCompanyType2Inline]
class CustomerCompanyType1Inline(admin.TabularInline):
model = CustomerCompany
def queryset(self, request):
return super(CustomerCompanyType1Inline, self).queryset(request).filter(type=1)
class CustomerCompanyType2Inline(admin.TabularInline):
model = CustomerCompany
def queryset(self, request):
return super(CustomerCompanyType2Inline, self).queryset(request).filter(type=2)
到这里为止一切都很好,但是要为
InlineModelAdmin
添加新记录,我仍然需要在type
上显示CustomerCompany
的AdminForm
字段,因为我无法覆盖save
的InlineModelAdmin
方法,例如:class CustomerCompanyType2Inline(admin.TabularInline):
model = CustomerCompany
def queryset(self, request):
return super(CustomerCompanyType2Inline, self).queryset(request).filter(type=2)
#Following override do not work
def save_model(self, request, obj, form, change):
obj.type=2
obj.save()
使用信号也不是解决方案,因为我的信号
sender
将是相同的Model
,所以我无法检测到哪个InlineModelAdmin
发送了它,什么type
必须是...有没有一种方法可以让我在保存之前设置
type
字段? 最佳答案
Alasdair的答案没有错,但是它有一些痛点,可能会引起问题。首先,通过使用form
作为变量名遍历表单集,您实际上覆盖了传递给form
方法的值。这没什么大不了的,但是由于您可以直接从表单集中进行保存而无需提交,因此最好这样做。其次,所有重要的formset.save_m2m()
都被排除在答案之外。实际的Django docs建议以下内容:
def save_formset(self, request, form, formset, change):
instances = formset.save(commit=False)
for instance in instances:
# Do something with `instance`
instance.save()
formset.save_m2m()
您将遇到的问题是,
save_formset
方法必须在父ModelAdmin
而不是内联代码上进行操作,并且从那里开始,您无法知道实际上正在使用哪个内联代码。如果您的obj具有两个“类型”,并且所有字段都相同,那么您应该使用代理模型,并且实际上可以覆盖每个模型的save方法以自动设置适当的类型。class CustomerCompanyType1(CustomerCompany):
class Meta:
proxy = True
def save(self, *args, **kwargs):
self.type = 1
super(CustomerCompanyType1, self).save(*args, **kwargs)
class CustomerCompanyType2(CustomerCompany):
class Meta:
proxy = True
def save(self, *args, **kwargs):
self.type = 2
super(CustomerCompanyType2, self).save(*args, **kwargs)
然后,您不需要对内联进行任何特殊处理。只需更改您现有的内联管理类以使用其适当的代理模型,一切便会自行解决。
关于django - 覆盖保存在Django InlineModelAdmin上,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/8294889/