Ticket #17515: 17515.admin-filter-custom-templates.diff

File 17515.admin-filter-custom-templates.diff, 6.6 KB (added by Julien Phalip, 12 years ago)
  • django/contrib/admin/filters.py

    diff --git a/django/contrib/admin/filters.py b/django/contrib/admin/filters.py
    index b2d74ce..550683b 100644
    a b from django.contrib.admin.util import (get_model_from_relation,  
    1717
    1818class ListFilter(object):
    1919    title = None  # Human-readable title to appear in the right sidebar.
     20    template = 'admin/filter.html'
    2021
    2122    def __init__(self, request, params, model, model_admin):
    2223        # This dictionary will eventually contain the request's query string
  • django/contrib/admin/templatetags/admin_list.py

    diff --git a/django/contrib/admin/templatetags/admin_list.py b/django/contrib/admin/templatetags/admin_list.py
    index ba3d132..067553b 100644
    a b from django.utils.text import capfirst  
    1313from django.utils.translation import ugettext as _
    1414from django.utils.encoding import smart_unicode, force_unicode
    1515from django.template import Library
    16 
     16from django.template.loader import get_template
     17from django.template.context import Context
    1718
    1819register = Library()
    1920
    def search_form(cl):  
    360361        'search_var': SEARCH_VAR
    361362    }
    362363
    363 @register.inclusion_tag('admin/filter.html')
     364@register.simple_tag()
    364365def admin_list_filter(cl, spec):
    365     return {'title': spec.title, 'choices' : list(spec.choices(cl))}
     366    t = get_template(spec.template)
     367    ctx = Context({'title': spec.title, 'choices' : list(spec.choices(cl)), 'spec': spec})
     368    return t.render(ctx)
    366369
    367370@register.inclusion_tag('admin/actions.html', takes_context=True)
    368371def admin_actions(context):
  • docs/ref/contrib/admin/index.txt

    diff --git a/docs/ref/contrib/admin/index.txt b/docs/ref/contrib/admin/index.txt
    index 76ea780..c40ce89 100644
    a b subclass::  
    697697
    698698      .. note::
    699699
    700           The ``FieldListFilter`` API is currently considered internal
    701           and prone to refactoring.
     700        The ``FieldListFilter`` API is currently considered internal and prone
     701        to refactoring.
     702
     703    .. versionadded:: 1.4
     704
     705    It is possible to specify a custom template for rendering a list filter::
     706
     707        class FilterWithCustomTemplate(SimpleListFilter):
     708            template = "custom_template.html"
     709
     710    See the default template provided by django (``admin/filter.html``) for
     711    a concrete example.
    702712
    703713.. attribute:: ModelAdmin.list_max_show_all
    704714
  • tests/regressiontests/admin_views/admin.py

    diff --git a/tests/regressiontests/admin_views/admin.py b/tests/regressiontests/admin_views/admin.py
    index 8c5b511..4582938 100644
    a b from django.conf.urls import patterns, url  
    1313from django.db import models
    1414from django.forms.models import BaseModelFormSet
    1515from django.http import HttpResponse
     16from django.contrib.admin import BooleanFieldListFilter
    1617
    1718from .models import (Article, Chapter, Account, Media, Child, Parent, Picture,
    1819    Widget, DooHickey, Grommet, Whatsit, FancyDoodad, Category, Link,
    from .models import (Article, Chapter, Account, Media, Child, Parent, Picture,  
    2526    CoverLetter, Story, OtherStory, Book, Promo, ChapterXtra1, Pizza, Topping,
    2627    Album, Question, Answer, ComplexSortedPerson, PrePopulatedPostLargeSlug,
    2728    AdminOrderedField, AdminOrderedModelMethod, AdminOrderedAdminMethod,
    28     AdminOrderedCallable, Report)
     29    AdminOrderedCallable, Report, Color2)
    2930
    3031
    3132def callable_year(dt_value):
    class ReportAdmin(admin.ModelAdmin):  
    512513                name='cable_extra'),
    513514        )
    514515
     516class CustomTemplateBooleanFieldListFilter(BooleanFieldListFilter):
     517    template = 'custom_filter_template.html'
     518
     519class CustomTemplateFilterColorAdmin(admin.ModelAdmin):
     520    list_filter = (('warm', CustomTemplateBooleanFieldListFilter),)
     521
    515522site = admin.AdminSite(name="admin")
    516523site.register(Article, ArticleAdmin)
    517524site.register(CustomArticle, CustomArticleAdmin)
    site.register(AdminOrderedField, AdminOrderedFieldAdmin)  
    581588site.register(AdminOrderedModelMethod, AdminOrderedModelMethodAdmin)
    582589site.register(AdminOrderedAdminMethod, AdminOrderedAdminMethodAdmin)
    583590site.register(AdminOrderedCallable, AdminOrderedCallableAdmin)
     591site.register(Color2, CustomTemplateFilterColorAdmin)
    584592
    585593# Register core models we need in our tests
    586594from django.contrib.auth.models import User, Group
  • tests/regressiontests/admin_views/models.py

    diff --git a/tests/regressiontests/admin_views/models.py b/tests/regressiontests/admin_views/models.py
    index 0029fcc..0e0fa81 100644
    a b class Color(models.Model):  
    106106    def __unicode__(self):
    107107        return self.value
    108108
     109# we replicate Color to register with another ModelAdmin
     110class Color2(Color):
     111    class Meta:
     112        proxy = True
    109113
    110114class Thing(models.Model):
    111115    title = models.CharField(max_length=20)
  • new file tests/regressiontests/admin_views/templates/custom_filter_template.html

    diff --git a/tests/regressiontests/admin_views/templates/custom_filter_template.html b/tests/regressiontests/admin_views/templates/custom_filter_template.html
    new file mode 100644
    index 0000000..e5c9a8e
    - +  
     1<h3>By {{ filter_title }} (custom)</h3>
     2<ul>
     3{% for choice in choices %}
     4    <li{% if choice.selected %} class="selected"{% endif %}>
     5    <a href="{{ choice.query_string|iriencode }}">{{ choice.display }}</a></li>
     6{% endfor %}
     7</ul>
  • tests/regressiontests/admin_views/tests.py

    diff --git a/tests/regressiontests/admin_views/tests.py b/tests/regressiontests/admin_views/tests.py
    index b0120ce..b05683a 100644
    a b  
    11# coding: utf-8
    22from __future__ import with_statement, absolute_import
    33
     4import os
    45import re
    56import datetime
    67import urlparse
    class AdminViewBasicTest(TestCase):  
    573574        except SuspiciousOperation:
    574575            self.fail("Filters should be allowed if they are defined on a ForeignKey pointing to this model")
    575576
     577    def test_filter_with_custom_template(self):
     578        """
     579        Ensure that one can use a custom template to render an admin filter.
     580        Refs #17515.
     581        """
     582        template_dirs = settings.TEMPLATE_DIRS + (
     583            os.path.join(os.path.dirname(__file__), 'templates'),)
     584        with self.settings(TEMPLATE_DIRS=template_dirs):
     585            response = self.client.get("/test_admin/admin/admin_views/color2/")
     586            self.assertTrue('custom_filter_template.html' in [t.name for t in response.templates])
     587
     588
    576589class AdminJavaScriptTest(AdminViewBasicTest):
    577590    urls = "regressiontests.admin_views.urls"
    578591
Back to Top