是搜索查询集的__contains过滤器的任何用途?

时间:2013-01-11 10:21:09

标签: django filter elasticsearch contains django-haystack

我在其中一个项目中使用django-haystack v2.0.0运行pyelasticsearch v0.3。我有SearchView呈现列表模板,我想整合结果过滤。搜索运行正常,但我使用的过滤器根本不工作?我使用以下过滤器 __contains __lte __gte ,但似乎没有一个过滤器结果列表的差异。

所以说,我根据搜索字词从SearchView提取了10个结果。在同一模板上,我有一个过滤器表单(使用GET方法)并调用相同的SearchView。现在在SearchView下我有一个自定义私有_filter_results方法,定义如下。

    def _filter_results(results, filters):
        """  
        This method would return the filtered search results, based on
        the filters applied by a user.
        """

        for item in filters:
            if item == 'location':
                results = results.filter(locations__contains=filters[item])
                print results
            if item == 'age_min':
                results = results.filter(workex_min__gte=filters[item])
            if item == 'age_max':
                results = results.filter(workex_max__lte=filters[item])
        return results

现在,我将结果传递给模板,如下所示:

context {'results' : _filter_results(self.results, self.result_filters)}

self.result_filters是我在SearchView的{​​{1}}方法中设置的过滤词典,它看起来像这样。

__call__

我没有收到任何错误,我已经仔细检查过每个过滤器值是否传递给{ 'location' : request.GET.get('location'), 'age_min' : request.GET.get('age_min'), 'age_max' : request.GET.get('age_max'), } 方法。但结果仍然保持不变。

如果在10个条目的结果列表中,我尝试使用其中没有包含该位置的位置进行过滤,我仍然会得到相同10个条目的结果。可能是什么原因?

1 个答案:

答案 0 :(得分:1)

我没有将Haystack与ElasticSearch一起使用,但在Solr中广泛使用它,但它也应该与ElasticSearch一样。

您应该使用results.narrow()方法而不是filter。 Filter方法基本上会将过滤器附加到主要的初始查询项,并在它们之间运行“OR”查询,因为默认运算符在haystack中设置为“OR”。

narrow()方法专门用于过滤初始结果集并进一步细化它们,还有利于使用narrow运行过滤器查询,因为在SearchEngine中构造的查询是不同的,并且更好地利用内置缓存。

def _filter_results(results, filters):
    """  
    This method would return the filtered search results, based on
    the filters applied by a user.
    """

    for item in filters:
        if item == 'location':
            results = results.narrow('locations:%s' % filters[item])
            print results
        if item == 'age_min':
            results = results.narrow('workex_min:[%s TO *]' % filters[item])
        if item == 'age_max':
            results = results.narrow('workex_max:[* TO %s]' % filters[item])
    return results

这又是它与Solr一起工作的方式,但是haystack方法概念是相同的,唯一的区别在于每个SearchEngine的后端文件。您应该查看haystack / backends / elasticsearch_backend.py以便更好地理解。

另请参阅FacetedSearchView和FacetedSearchForm