了解这个Django搜索功能

时间:2017-01-07 20:31:08

标签: python django django-models

我最近为Django Web应用程序实现了一个搜索功能(它运行得很好)。但是,我并不完全理解代码的工作原理。你能否解释一下发生了什么,特别是:

  • “get_queryset”& “get_contest_data”(views.py)一起工作?
  • 搜索请求(来自模板)如何知道转到“get_queryset”?
  • 什么是返回qs?

查看:

from django.db.models import Q

class ProductListView(ListView):
    model = Product
    queryset = Product.objects.all()

def get_context_data(self, *args, **kwargs):
    context = super(ProductListView, self).get_context_data(*args, **kwargs)
    context["now"] = timezone.now()
    context["query"] = self.request.GET.get("q") #None
    return context

def get_queryset(self, *args, **kwargs):
    qs = super(ProductListView, self).get_queryset(*args, **kwargs)
    query = self.request.GET.get("q")
    if query:
        qs = self.model.objects.filter(
            Q(title__icontains=query) |
            Q(description__icontains=query)
            )
        try:
            qs2 = self.model.objects.filter(
                Q(price=query)
            )
            qs = (qs | qs2).distinct()
        except:
            pass
    return qs

模板

<form class="navbar-form navbar-left" method="GET" role="search"   action='{% url "products" %}'>
<div class="form-group">
<input type="text" class="form-control" placeholder="Search" name="q">
</div>
</form>

1 个答案:

答案 0 :(得分:1)

该模板告诉Django使用参数“q”(例如www.example.com/products?q=search_term)向指定网址的后端发送GET请求

Django将url和GET http方法与ProductListView类匹配,其中q作为参数传递

ListView继承自BaseListView,它从您在代码中扩展的方法self.get_context_data()设置上下文。 BaseListView继承自MultipleObjectMixin,它实现了您扩展的self.get_queryset()方法。

简而言之,CBV(类基本视图)具有一个继承网络,用于定义可以看到here的不同方法。由于这个继承链,许多方法对你隐藏,所以你要么需要阅读文档,要么更好地学习Django源代码来弄清楚发生了什么。

至于返回qs,qs是您在扩展get_queryset()方法中返回的查询集。

  • 你的价值q
  • 过滤标题或说明中值为q的任何模型,并将其存储为qs中的查询集
  • 过滤任何价格为q且在qs2中将其存储为查询集的模型
  • 合并查询集qs和qs2并确保每条记录都是唯一的,然后将该查询集返回为ProductListView使用的查询集