【问题标题】:Django - How to set the request in the admin form?Django - 如何在管理表单中设置请求?
【发布时间】:2019-06-06 15:21:17
【问题描述】:

我有一个使用请求对象的表单:

class FooForm(forms.ModelForm):

    class Meta:
        model = Foo
        fields = ('title', )

    def __init__(self, *args, **kwargs):
        self.request = kwargs.pop('request')
        super().__init__(*args, **kwargs)

在我看来,每当我想实例化表单时,只需执行以下操作即可:

class FooCreateView(LoginRequiredMixin, CreateView):
    model = Foo
    form_class = FooForm

    def get_form_kwargs(self):
        kwargs = super(FooCreateView, self).get_form_kwargs()
        kwargs.update({'request': self.request})
        return kwargs

现在,我想在管理面板中使用相同的表单,所以我执行以下操作:

class FooAdmin(admin.ModelAdmin):
    form = FooForm

但是繁荣!它死了:

KeyError at /admin/foo/foo/add/
'request'

我尝试执行以下操作,但没有成功

def get_form(self, request, *args,  **kwargs):
    form = super(FooAdmin, self).get_form(request, *args, **kwargs)
    form.request = request
    kwargs['request'] = request
    return form

总之,有没有办法将请求传递给管理表单?

【问题讨论】:

    标签: django django-forms django-admin


    【解决方案1】:

    get_form() 方法只返回类,而不是它的实例。表单的实例化隐藏在ModelAdminadd_viewchange_view 方法中。 你可以通过在 get_form 方法中创建一个新的表单类来解决这个问题:

    def get_form(self, request, obj=None, **kwargs):
    
        FooForm = super(FooAdmin, self).get_form(request, obj, **kwargs)
    
        class RequestFooForm(FooForm):
            def __new__(cls, *args, **kwargs):
                kwargs['request'] = request
                return FooForm(*args, **kwargs)
    
        return RequestFooForm
    

    否则,如果您只是在保存期间需要访问权限,您可能还可以查看模型管理员的 save_formsave_model 方法。

    【讨论】:

    • 太棒了!正是我需要的。谢谢
    • 多么巧妙的解释!谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-05-04
    • 2018-06-12
    • 2017-11-15
    • 1970-01-01
    • 2014-02-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多