如何将一个对象的 Django 管理页面的链接添加到相关对象的管理页面?

问题描述

为了处理 django-admin 中的缺少嵌套内联,我在其中两个模板中加入了特殊情况,以在两个模型的管理员更改页面和内联管理员之间创建链接.

To deal with the lack of nested inlines in django-admin, I've put special cases into two of the templates to create links between the admin change pages and inline admins of two models.

我的问题是:如何干净利落地创建从一个模型的管理员更改页面或内联管理员到相关模型的管理员更改页面或内联管理员的链接,而不会在模板中出现讨厌的黑客攻击?

我想要一个通用的解决方案,可以应用于任何模型的管理员更改页面或内联管理员.

I would like a general solution that I can apply to the admin change page or inline admin of any model.

我有一个模型,post(不是它的真名),它既是 blog 管理页面上的内联,也有自己的管理页面.它不能只是内联的原因是它具有带有外键的模型,只有在使用它编辑时才有意义,并且只有在使用 blog 编辑时才有意义.

I have one model, post (not its real name) that is both an inline on the blog admin page, and also has its own admin page. The reason it can't just be inline is that it has models with foreign keys to it that only make sense when edited with it, and it only makes sense when edited with blog.

对于 post 管理页面,我将fieldset.html"的一部分从:

For the post admin page, I changed part of "fieldset.html" from:

{% if field.is_readonly %}
    <p>{{ field.contents }}</p>
{% else %}
    {{ field.field }}
{% endif %}

{% if field.is_readonly %}
    <p>{{ field.contents }}</p>
{% else %}
    {% ifequal field.field.name "blog" %}
        <p>{{ field.field.form.instance.blog_link|safe }}</p>
    {% else %}
        {{ field.field }}
    {% endifequal %}
{% endif %}

创建一个到 blog 管理页面的链接,其中 blog_link 是模型上的一个方法:

to create a link to the blog admin page, where blog_link is a method on the model:

def blog_link(self):
      return '<a href="%s">%s</a>' % (reverse("admin:myblog_blog_change",  
                                        args=(self.blog.id,)), escape(self.blog))

我在 field.field.form.instance 之外的任何地方都找不到 blog 实例的 id.

I couldn't find the id of the blog instance anywhere outside field.field.form.instance.

blog 管理页面上,其中 post 是内联的,我从以下位置修改了stacked.html"的一部分:

On the blog admin page, where post is inline, I modified part of "stacked.html" from:

<h3><b>{{ inline_admin_formset.opts.verbose_name|title }}:</b>&nbsp;
<span class="inline_label">{% if inline_admin_form.original %}
    {{ inline_admin_form.original }}
{% else %}#{{ forloop.counter }}{% endif %}</span>

<h3><b>{{ inline_admin_formset.opts.verbose_name|title }}:</b>&nbsp;
<span class="inline_label">{% if inline_admin_form.original %}
    {% ifequal inline_admin_formset.opts.verbose_name "post" %}
    <a href="/admin/myblog/post/{{ inline_admin_form.pk_field.field.value }}/">
            {{ inline_admin_form.original }}</a>
{% else %}{{ inline_admin_form.original }}{% endifequal %}
{% else %}#{{ forloop.counter }}{% endif %}</span>

创建一个到 post 管理页面的链接,因为在这里我能够找到存储在外键字段中的 id.

to create a link to the post admin page since here I was able to find the id stored in the foreign key field.

我确信有一种更好、更通用的方法可以在不重复自己的情况下添加管理表单的链接;这是什么?


解决方案

Django 1.8 中的新功能:show_change_link 用于内联管理员.

New in Django 1.8 : show_change_link for inline admin.

在内联模型中将 show_change_link 设置为 True(默认为 False),以便内联对象具有指向其更改表单的链接(它们可以有自己的内联).

Set show_change_link to True (False by default) in your inline model, so that inline objects have a link to their change form (where they can have their own inlines).

from django.contrib import admin

class PostInline(admin.StackedInline):
    model = Post
    show_change_link = True
    ...

class BlogAdmin(admin.ModelAdmin):
    inlines = [PostInline]
    ...

class ImageInline(admin.StackedInline):
    # Assume Image model has foreign key to Post
    model = Image
    show_change_link = True
    ...

class PostAdmin(admin.ModelAdmin):
    inlines = [ImageInline]
    ...

admin.site.register(Blog, BlogAdmin)
admin.site.register(Post, PostAdmin)

相关文章