2016-01-20 84 views
9

我已经为我的模型定义了一个自定义的管理操作,它可以按预期完美工作。我还着眼于在SO上添加一个按钮到管理变更页面的多种方式。只有我缺少的步骤是如何使更改页面中的按钮执行我的自定义管理操作与当前对象。Django:如何将自定义按钮添加到管理更改执行管理操作的表单页面?

目标是允许管理员单独检查每个对象并对它们执行操作,而无需返回列表视图,选择检查对象并从列表中执行操作。

我定制的管理操作是这样的:

def admin_apply_change(modeladmin, request, queryset): 
    # loop over objects in query set and perform action 

我假设有调用管理变化的形式这个动作,其中queryset将只包含简单和干净的方式当前打开的对象管理员正在看。

注意:如果按钮是在变化形式的底部,旁边Save按钮,而不是在顶部History是这是不是很明显这将是preferrable。

解决方案

为解决一看便知通过Remi。为了使其发挥作用需要以下更正:

1:在response_change初始化一些变量的覆盖丢失:

opts = self.model._meta 
pk_value = obj._get_pk_val() 
preserved_filters = self.get_preserved_filters(request) 

2:新的包含标签custom_submit_row应放置在templatetags而不是在管理员(请参阅docs for custom templatetags

3:这是您可能会放松一段时间的疏忽。在change_form.html你不仅要更改建议的行:

{% if save_on_top %}{% block submit_buttons_top %}{% submit_row %}{% endblock %}{% endif %} 

而且在底部更重要的线,其中submit_row出现:

{% block submit_buttons_bottom %}{% submit_row %}{% endblock %} 

(它正好位于change_form.html的JavaScript块以上)

回答

13

您可以查看change_form_template并将其设置为您的自定义模板并覆盖response_change方法:

class MyModelAdmin(admin.ModelAdmin): 

    # A template for a customized change view: 
    change_form_template = 'path/to/your/custom_change_form.html' 

    def response_change(self, request, obj): 
     opts = self.model._meta 
     pk_value = obj._get_pk_val() 
     preserved_filters = self.get_preserved_filters(request) 

     if "_customaction" in request.POST: 
      # handle the action on your obj 
      redirect_url = reverse('admin:%s_%s_change' % 
           (opts.app_label, opts.model_name), 
           args=(pk_value,), 
           current_app=self.admin_site.name) 
      redirect_url = add_preserved_filters({'preserved_filters': preserved_filters, 'opts': opts}, redirect_url) 
      return HttpResponseRedirect(redirect_url) 
     else: 
      return super(MyModelAdmin, self).response_change(request, obj) 
site-packages/django/contrib/admin/templates/change_form.html

复制change_form.html和编辑该行44

{% if save_on_top %}{% block submit_buttons_top %}{% submit_row %}{% endblock %}{% endif %} 

{% if save_on_top %}{% block submit_buttons_top %}{% custom_submit_row %}{% endblock %}{% endif %} 

同时检查线路:

{% block submit_buttons_bottom %}{% submit_row %}{% endblock %} 

刚刚的JavaScript块以上。

然后你就可以在你的admin.py地方注册一个新的包含标签或将其添加到templatetags:

@register.inclusion_tag('path/to/your/custom_submit_line.html', takes_context=True) 
def custom_submit_row(context): 
    """ 
    Displays the row of buttons for delete and save. 
    """ 
    opts = context['opts'] 
    change = context['change'] 
    is_popup = context['is_popup'] 
    save_as = context['save_as'] 
    ctx = { 
     'opts': opts, 
     'show_delete_link': (
      not is_popup and context['has_delete_permission'] and 
      change and context.get('show_delete', True) 
     ), 
     'show_save_as_new': not is_popup and change and save_as, 
     'show_save_and_add_another': (
      context['has_add_permission'] and not is_popup and 
      (not save_as or context['add']) 
     ), 
     'show_save_and_continue': not is_popup and context['has_change_permission'], 
     'is_popup': is_popup, 
     'show_save': True, 
     'preserved_filters': context.get('preserved_filters'), 
    } 
    if context.get('original') is not None: 
     ctx['original'] = context['original'] 
    return ctx 

custom_submit_line.html的内容:

{% load i18n admin_urls %} 
<div class="submit-row"> 
{% if show_save %}<input type="submit" value="{% trans 'Save' %}" class="default" name="_save" />{% endif %} 
{% if show_delete_link %} 
    {% url opts|admin_urlname:'delete' original.pk|admin_urlquote as delete_url %} 
    <p class="deletelink-box"><a href="{% add_preserved_filters delete_url %}" class="deletelink">{% trans "Delete" %}</a></p> 
{% endif %} 
{% if show_save_as_new %}<input type="submit" value="{% trans 'Save as new' %}" name="_saveasnew" />{% endif %} 
{% if show_save_and_add_another %}<input type="submit" value="{% trans 'Save and add another' %}" name="_addanother" />{% endif %} 
{% if show_save_and_continue %}<input type="submit" value="{% trans 'Save and continue editing' %}" name="_continue" />{% endif %} 

<input type="submit" value="{% trans 'Custom Action' %}" name="_customaction" /> 

</div> 

这是一个很大的代码,但主要是复制/粘贴。希望有所帮助。

+0

谢谢。这解决了我的问题以及一些小的更正。在我的问题更新中看到它们。如果您可以更新您的答案以纳入这些更正,那将会很好。 – dsalaj

3

大多数人可能会毫不犹豫地做到这一点,虽然从答案中不清楚,管理员变更表单应该简单地扩展而不是完全覆盖。

custom_change_form.html

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

{% if save_on_top %}{% block submit_buttons_top %}{% custom_submit_row %}{% endblock %}{% endif %} 

{% block submit_buttons_bottom %}{% custom_submit_row %}{% endblock %} 
相关问题