【问题标题】:Django-Filter - Removing filter options that will return emptyDjango-Filter - 删除将返回空的过滤器选项
【发布时间】:2020-12-16 15:27:01
【问题描述】:

我觉得我在这里遗漏了一些非常明显的东西。我正在使用 Django-Filter 来过滤 ListView,除了您在下拉菜单中获得的选项还包括将返回空搜索查询的选项之外,它运行良好。

我已经在我的数据库中预先填充了一堆我将需要但目前尚未使用的数据,特别是“Nations”和“Region”模型。

Models.py:

class Nation(models.Model):
    name = models.CharField(max_length=200)
    slug = models.SlugField(max_length=100, unique=False)

class Region(models.Model):
    name = models.CharField(max_length=200)
    slug = models.SlugField(max_length=100, unique=False)
    nation = models.ForeignKey(Nation, on_delete=models.PROTECT)

class Business(models.Model):
    name = models.CharField(max_length=200)
    nation = models.ManyToManyField(Nation, blank=True,)
    region = models.ManyToManyField(Region, blank=True,)

Filters.py:

from business.models import Business, BusinessCategory
from locations.models import Nation, Region
import django_filters


class BusinessFilter(django_filters.FilterSet):
    nation = django_filters.ModelChoiceFilter(
        field_name='nation', lookup_expr='isnull',
        queryset=Nation.objects.all().order_by('name')
    )

    class Meta:
        model = Business
        fields = ['business_category', 'nation', 'region']

View.Py:

class BusinessIndexView(ListView):
    paginate_by = 6
    template_name = "business/index.html"
    context_object_name = 'all_business'

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        context['filter']= BusinessFilter(self.request.GET, queryset=self.get_queryset())
        return context

    def get_queryset(self):
        return Business.objects.filter(live=True).order_by('-id')

Filter.html:

{% load crispy_forms_tags %}
<div class="mb-2">
<form method="get">
{{filter.form|crispy}}
<button type="submit" class="btn btn-outline-success my-2 my-sm-0">Search</button>
<a class="btn btn-outline-warning my-2 my-sm-0" href="{% url 'business:index' %}">Reset</a>

</form>

</div>

Filters.py 是我知道它正在崩溃的地方。任何帮助将不胜感激。我已通读并尝试实现文档的相关部分(“Filtering the related queryset for ModelChoiceFilter”),但无济于事。

编辑: 所需的功能是一个简单的下拉过滤器,因此用户可以通过与企业相关联的国家/地区搜索企业。

示例:BBC、英国 - 电报、英国 - CNN、美国 - XYZ、美国 - 等等。

目前我有很多国家添加到数据库中,这些国家尚未与企业相关联,但将来会。我想从下拉列表中删除“空”国家,直到它们与它们相关联。

使用上面的示例,我的过滤器中列出了英国、美国和加拿大,但应该只显示英国和美国,因为没有与加拿大相关联。

【问题讨论】:

  • 从未使用过此库,但您是否有可能尝试通过 nation 进行过滤,这在 Nation 模型中不是有效字段?所以它返回查询集中的所有对象以进行下拉?
  • 这正是我认为正在发生的事情。我认为它应该说类似“queryset=Business.objects.filter(nation=is_valid_nation).order_by('name')”,但我不完全确定在这种情况下如何验证“is_valid_nation”
  • 能否再次更具体地描述预期的结果,我还没有完全明白。也许将其添加到帖子中。谢谢
  • 我用更好的描述更新了它

标签: python-3.x django django-filter django-filters


【解决方案1】:

你可以试试这个:

在你的模型中:

class Business(models.Model):
    name = models.CharField(max_length=200)
    nation = models.ManyToManyField(Nation, blank=True,related_name='businesses')
    region = models.ManyToManyField(Region, blank=True,)

过滤器.py

class BusinessFilter(django_filters.FilterSet):
    nation = django_filters.ModelChoiceFilter(
        field_name='nation', lookup_expr='isnull',
        queryset=Nation.objects.exclude(businesses__isnull=True).order_by('name')
    )

    class Meta:
        model = Business
        fields = ['business_category', 'nation', 'region']

【讨论】:

  • 效果很好!太感谢了。没想到这么简单哈哈
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-17
  • 2018-09-18
  • 1970-01-01
  • 2018-04-28
相关资源
最近更新 更多