将参数传递给 django admin 中的内联表单

Passing parameters to inline form in django admin

我有一个管理员 class 继承自 ModelAdmin:

class TemplateAdmin (admin.ModelAdmin):
    inlines = (TemplateAttributeInline, CompanyAttributeInline)
    list_display = ("name", "created", "updated","departments")
    list_filter = ['companies__company']
    list_editable = ("departments",)
    search_fields = ("name", "companies__company",)
    exclude = ("companies",)
    save_as = True

我想将一个参数传递给 TemplateAttributeInline,后者又会将参数传递给 TemplateAttributeForm。最好的方法是什么?

TemplateAttributeInline:

class TemplateAttributeInline (admin.TabularInline):
    model = TemplateAttribute
    extra = 0
    sortable_field_name = "display"
    form = TemplateAttributeForm

TemplateAttributeForm

class TemplateAttributeForm(forms.ModelForm):
    class Meta:
        model = Template
    def __init__(self,*args, **kwargs):
        super(TemplateAttributeForm, self).__init__(*args, **kwargs) 
        self.fields['attribute'].queryset = Attribute.objects.filter(#WANT TO FILTER BY THE ID OF THE COMPANY THAT OWNS THE TEMPLATE WE ARE EDITING ON THE ADMIN PAGE)

您可以创建一个 returns 一个 class 形式的函数:

def TemplateAttributeForm(param):

    class MyTemplateAttributeForm(forms.ModelForm):
        class Meta:
            model = Template
        def __init__(self,*args, **kwargs):
            super(TemplateAttributeForm, self).__init__(*args, **kwargs) 
            #do what ever you want with param

    return MyTemplateAttributeForm

在另一个函数中使用它来定义 TemplateAttributeInline

def TemplateAttributeInline(param):

        class MyTemplateAttributeInline (admin.TabularInline):
            model = TemplateAttribute
            extra = 0
            sortable_field_name = "display"
            form = TemplateAttributeForm(param)

        return MyTemplateAttributeInline 

最后,在您的 TemplateAdmin 定义中使用此函数:

class TemplateAdmin (admin.ModelAdmin):
    inlines = (TemplateAttributeInline(param), CompanyAttributeInline)
    ....

通过 , I added the following code to make the inline form dynamic. Here is the reference at django doc 补充回复。方法“get_inline_instances”在第一次“加载”、“保存”之后和“重新加载”时被调用。在“添加”事件中,None 被传递。

这里,“obj”是管理表单当前绑定到的模型实例。对于未绑定(添加新)表单,它是“None”。您可以传递它的任何属性,而不是直接传递模型实例“obj”,例如obj.id。在这种情况下,您需要先检查实例是否不是 None.

class TemplateAdmin (admin.ModelAdmin):
   ...
   inlines = (TemplateAttributeInline(param), CompanyAttributeInline)
   ...
   def get_inline_instances(self, request, obj=None): 
     return  [
         TemplateAttributeInline(obj)(self.model, self.admin_site), 
         CompanyAttributeInline(self.model, self.admin_site), 
       ]