# admin_list.py
from django.contrib.admin.templatetags.admin_list import *


@register.simple_tag
def admin_list_filter(cl, spec):
"""
Django stock admin_list_filter is an inclusion_tag, we want to run spec.output instead.
"""
    return spec.output(cl)


# filterspecs.py
from django.contrib.admin.filterspecs import *
from django.utils.translation import ugettext as _

class UserFieldFilterSpec(RelatedFilterSpec):
    def __init__(self, f, request, *args, **kwargs):
        super(UserFieldFilterSpec, self).__init__(f, request, *args, **kwargs)
        self.lookup_kwarg = '%s__username__exact' % self.field_path
        self.lookup_val = request.GET.get(self.lookup_kwarg, None)

    def output(self, cl):
        t = []
        if self.has_output():
            t.append(_(u'<h3>By %s:</h3>\n<ul>\n') % escape(self.title()))
            t.append("""\
                <script type="text/javascript">
                    django.jQuery(function($) {
                        $('input.filter-user-fk')
                            .change(function() {
                                var $next = $(this).next()
                                var val = $(this).val()
                                $next.attr('href', val ? $next.attr('data-querystring').replace('%25s', val) : '#')
                            })
                    })
                </script>
            """)
            for choice in self.choices(cl):
                if choice['type'] == 'input':
                    t.append(u'<li%s><input class="filter-user-fk" type="text" value="%s"><a data-querystring="%s" href="#">&gt;</a></li>\n' % \
                        ((choice['selected'] and ' class="selected"' or ''),
                         choice['display'],
                         iri_to_uri(choice['query_string'])))
                else:
                    t.append(u'<li%s><a href="%s">%s</a></li>\n' % \
                        ((choice['selected'] and ' class="selected"' or ''),
                         iri_to_uri(choice['query_string']),
                         choice['display']))
            t.append('</ul>\n\n')
        return mark_safe("".join(t))

    def choices(self, cl):
        from django.contrib.admin.views.main import EMPTY_CHANGELIST_VALUE
        yield {
            'selected': self.lookup_val is None and not self.lookup_val_isnull,
            'query_string': cl.get_query_string({}, [self.lookup_kwarg, self.lookup_kwarg_isnull]),
            'type': 'link',
            'display': _('All')
        }
        yield {
            'selected': bool(self.lookup_val),
            'query_string': cl.get_query_string({self.lookup_kwarg: '%s'}, [self.lookup_kwarg_isnull]),
            'type': 'input',
            'display': self.lookup_val or ''
        }
        if isinstance(self.field, models.related.RelatedObject) \
           and self.field.field.null or hasattr(self.field, 'rel') \
           and self.field.null:
            yield {
                'selected': bool(self.lookup_val_isnull),
                'query_string': cl.get_query_string({self.lookup_kwarg_isnull: 'True'}, [self.lookup_kwarg]),
                'type': 'link',
                'display': EMPTY_CHANGELIST_VALUE
            }
from django.contrib.auth.models import User
FilterSpec.filter_specs.insert(0, (lambda f: isinstance(f, models.ForeignKey) and f.rel.to == User, UserFieldFilterSpec))
