【问题标题】:How to add custom view to django admin interface?如何将自定义视图添加到 django 管理界面?
【发布时间】:2019-10-08 19:27:33
【问题描述】:

我的 django 管理界面如下所示:

现在我想添加一个与模型不对应的视图。

我可以覆盖上面页面的模板并添加一个自定义链接。但我认为这看起来很难看。

覆盖admin/index.html的示例:

{% extends "admin/index.html" %}

{% block content %}

{{ block.super }}
<div class="app-sonstiges module">
   ....
</div>
{% endblock %}

但也许有一种官方方法可以向管理界面添加自定义视图?

在我的例子中,我想提供一个可以执行tcptraceroute 到远程服务器的表单。我的应用的管理员需要这个。

我使用了相同的 html 标签。现在链接“tcptraceroute”看起来不错,但不幸的是消息下移了:

有没有办法获得像屏幕截图中的“Sontiges ... tcptraceroute”这样的自定义部分,而无需向下移动最新操作?

这是 html 结构的样子。我的&lt;div class="app-sonstiges"&gt; 在 content-main 下面:

【问题讨论】:

  • 不应该这样。你确定你没有忘记关闭添加到 index.html 的 HTML 片段中的一些标签吗?
  • @MarioOrlandi 我的部分 (&lt;div class="app-sonstiges module"&gt;...&lt;div&gt;) 是在之后,而不是在“content-main”中。我认为我的 html 中没有错字
  • mmhh 我明白了……您可以尝试在“.app-sonstiges”中添加一些 CSS 样式以使其浮动在左侧

标签: django django-admin


【解决方案1】:

这里有 3 个选项:

使用提供菜单的第三方包

这很简单,有一些很好的软件包支持管理员菜单,以及一些将您的项目添加到菜单的方法。

第 3 方包的一个示例是 django-admin-tools。缺点是有点难学。另一种选择是使用django-adminplus,但在撰写本文时,它不支持 Django 2.2。

使用 django 管理模板进行黑客攻击

您始终可以扩展管理模板并覆盖您想要的部分,如@Sardorbek 回答中所述,您可以从管理模板中复制一些部分并按照您想要的方式更改它们。

使用自定义管理站点

如果您的视图应该只在管理站点上起作用,那么您可以扩展 adminsite(可能还有 change the default),除了添加到模板的链接之外,您应该使用这种方法来定义您的仅管理员视图,因为它更容易以这种方式检查权限。

考虑到您已经扩展了 adminsite,现在您可以使用之前的方法将链接添加到模板,甚至可以扩展 get_app_list 方法,例如:

class MyAdminSite(admin.AdminSite):
    def get_app_list(self, request):
        app_list = super().get_app_list(request)
        app_list += [
            {
                "name": "My Custom App",
                "app_label": "my_test_app",
                # "app_url": "/admin/test_view",
                "models": [
                    {
                        "name": "tcptraceroute",
                        "object_name": "tcptraceroute",
                        "admin_url": "/admin/test_view",
                        "view_only": True,
                    }
                ],
            }
        ]
        return app_list

您还可以在向他们显示链接之前检查当前员工用户是否可以访问模块。 最后它看起来像这样:

【讨论】:

  • 很好的答案,谢谢!你推荐哪个第三方的 django 管理员包?
  • @guettli 这取决于您对该软件包的期望,django-admin-tools 很好,它保持默认 django 的外观和感觉,但它很难学习,还需要一些小技巧现在使用 django 2.2(问题中提到的一种解决方案),django-suit 更容易配置,但它的主题看起来有点旧(新版本正在开发中),你也可以使用支持侧边栏的 django-admin-bootstrap菜单,但是您需要使用我的答案中的第三个选项来添加新菜单项(我没有测试,但应该可以)
  • @PooyaMobasherBehrooz 我会将这些细节添加到您的答案中,这肯定会使其更加完整。
【解决方案2】:

这里的问题是您的div 不在main-content 内。我建议扩展admin/index.html

输入app/templates/admin/index.html

{% extends "admin/index.html" %}
{% load i18n static %}

{% block content %}
<div id="content-main">

{% if app_list %}
    {% for app in app_list %}
        <div class="app-{{ app.app_label }} module">
        <table>
        <caption>
            <a href="{{ app.app_url }}" class="section" title="{% blocktrans with name=app.name %}Models in the {{ name }} application{% endblocktrans %}">{{ app.name }}</a>
        </caption>
        {% for model in app.models %}
            <tr class="model-{{ model.object_name|lower }}">
            {% if model.admin_url %}
                <th scope="row"><a href="{{ model.admin_url }}">{{ model.name }}</a></th>
            {% else %}
                <th scope="row">{{ model.name }}</th>
            {% endif %}

            {% if model.add_url %}
                <td><a href="{{ model.add_url }}" class="addlink">{% trans 'Add' %}</a></td>
            {% else %}
                <td>&nbsp;</td>
            {% endif %}

            {% if model.admin_url %}
                {% if model.view_only %}
                <td><a href="{{ model.admin_url }}" class="viewlink">{% trans 'View' %}</a></td>
                {% else %}
                <td><a href="{{ model.admin_url }}" class="changelink">{% trans 'Change' %}</a></td>
                {% endif %}
            {% else %}
                <td>&nbsp;</td>
            {% endif %}
            </tr>
        {% endfor %}
        </table>
        </div>
    {% endfor %}

    <!-- here you could put your div -->
    <div class="app-sonstiges module">
    ....
    </div>
    <!-- here you could put your div -->
{% else %}
    <p>{% trans "You don't have permission to view or edit anything." %}</p>
{% endif %}
</div>
{% endblock %}

另一种方法是将自定义应用添加到app_list。但它更丑陋。所以我建议覆盖模板。

我假设您在AdminSite 中覆盖get_urls

【讨论】:

    【解决方案3】:

    如果您需要自定义页面来处理用户输入(来自表单),您可能想尝试一下django-etc 1.3.0+:

        from etc.admin import CustomModelPage
    
        class MyPage(CustomModelPage):
        
            title = 'My custom page'  # set page title
    
            # Define some fields you want to proccess data from.
            my_field = models.CharField('some title', max_length=10)
    
            def save(self):
                # Here implement data handling.
                super().save()
    
        # Register the page within Django admin.
        MyPage.register()
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-12-05
      • 2018-06-27
      • 1970-01-01
      • 1970-01-01
      • 2016-04-17
      • 1970-01-01
      • 2012-12-11
      • 1970-01-01
      相关资源
      最近更新 更多