是否可以将 Django Haystack 搜索与“内置”QuerySet 过滤操作相结合,特别是使用 SearchQuerySet 不支持的 Q() 实例和查找类型进行过滤?以任一顺序:
haystack-searched -> queryset-filtered
或者
queryset-filtered -> haystack-searched
浏览 Django Haystack 文档并没有给出如何做到这一点的任何指示。
是否可以将 Django Haystack 搜索与“内置”QuerySet 过滤操作相结合,特别是使用 SearchQuerySet 不支持的 Q() 实例和查找类型进行过滤?以任一顺序:
haystack-searched -> queryset-filtered
或者
queryset-filtered -> haystack-searched
浏览 Django Haystack 文档并没有给出如何做到这一点的任何指示。
您可以使用对象的 PK 根据 Haystack 搜索的结果过滤您的查询集:
def view(request):
if request.GET.get('q'):
from haystack import ModelSearchForm
form = ModelSearchForm(request.GET, searchqueryset=None, load_all=True)
searchqueryset = form.search()
results = [ r.pk for r in searchqueryset ]
docs = Document.objects.filter(pk__in=results)
# do something with your plain old regular queryset
return render_to_response('results.html', {'documents': docs});
不确定这是如何扩展的,但是对于小型结果集(在我的情况下为几百个),这可以正常工作。
从文档:
SearchQuerySet.load_all(self)
有效地填充搜索结果中的对象。如果不使用此方法,则数据库查找是基于每个对象进行的,从而导致对数据库的多次单独访问。如果使用 load_all,SearchQuerySet 会将相似的对象分组到一个查询中,从而产生与返回的不同对象类型一样多的查询。
http://django-haystack.readthedocs.org/en/latest/searchqueryset_api.html#load-all
因此,在您拥有过滤后的 SQS 之后,您可以对其执行 load_all() 并通过 SearchResult.object 访问数据库对象。例如
sqs = SearchQuerySet()
# filter as needed, then load_all
sqs = sqs.load_all()
for result in sqs:
my_obj = result.object
# my_obj is a your model object
如果你想跟上相关性,你必须通过 "object" 从数据库中访问对象:
模板中的示例:
{% for result in results %}
{{ result.object.title }}
{{ result.objects.author }}
{% endfor %}
但这真的很糟糕,因为 haystack 会在每个结果上发出额外的请求,例如“SELECT * FROM blah WHERE id = 42”。
似乎您正在尝试从数据库中获取这些对象,因为您没有在索引中添加一些额外的字段,不是吗?如果您在 SearchIndex 中添加标题和作者,那么您可以使用您的结果:
{% for result in results %}
{{ result.title }}
{{ result.author }}
{% endfor %}
并避免一些额外的查询。