Django Haystack - Show results without needing a search query? Django Haystack - Show results without needing a search query? django django

Django Haystack - Show results without needing a search query?


If anyone is still looking, there's a simple solution suggested in haystack code:

https://github.com/toastdriven/django-haystack/blob/master/haystack/forms.py#L34

class SearchForm(forms.Form):    def no_query_found(self):    """    Determines the behavior when no query was found.    By default, no results are returned (``EmptySearchQuerySet``).    Should you want to show all results, override this method in your    own ``SearchForm`` subclass and do ``return self.searchqueryset.all()``.    """    return EmptySearchQuerySet()


Why No Results?

I imagine you're using a search template similar to the one in the haystack getting started documentation. This view doesn't display anything if there is no query:

{% if query %}    {# Display the results #}{% else %}    {# Show some example queries to run, maybe query syntax, something else? #}{% endif %}

The second problem is that the default search form's search() method doesn't actually search for anything unless there's a query.

Getting Results

To get around this, I'm using a custom search form. Here's an abbreviated sample:

class CustomSearchForm(SearchForm):    ...    def search(self):        # First, store the SearchQuerySet received from other processing.        sqs = super(CustomSearchForm, self).search()        if not self.is_valid():          return sqs        filts = []        # Check to see if a start_date was chosen.        if self.cleaned_data['start_date']:            filts.append(SQ(created_date__gte=self.cleaned_data['start_date']))        # Check to see if an end_date was chosen.        if self.cleaned_data['end_date']:            filts.append(SQ(created_date__lte=self.cleaned_data['end_date']))        # Etc., for any other things you add        # If we started without a query, we'd have no search        # results (which is fine, normally). However, if we        # had no query but we DID have other parameters, then        # we'd like to filter starting from everything rather        # than nothing (i.e., q='' and tags='bear' should         # return everything with a tag 'bear'.)        if len(filts) > 0 and not self.cleaned_data['q']:            sqs = SearchQuerySet().order_by('-created_date')        # Apply the filters        for filt in filts:            sqs = sqs.filter(filt)        return sqs

Also, don't forget to change the view:

{% if query or page.object_list %}    {# Display the results #}{% else %}    {# Show some example queries to run, maybe query syntax, something else? #}{% endif %}

Actually, the view code is a little hackish. It doesn't distinguish query-less searches with no results from search with no parameters.

Cheers!


Look at SearchQuerySet.

This should be possible if color and price has been defined in your SearchIndex:

sqs = SearchQuerySet().filter(color="blue", price__range=(10,100))

You can limit the query to certain models by adding models(Model) to the SearchQuerySet. So if you want to limit your query to the model Item use:

sqs = SearchQuerySet().filter(color="blue", price__range=(10,100)).models(Item)