def test_words(self):
     # search strings with single words
     self.assertEqual([(None, 'word')], parse_search_terms('word'))
     self.assertEqual([(None, 'multiple'), (None, 'words')],
                      parse_search_terms('multiple words'))
     self.assertEqual([(None, 'extraneous'), (None, 'whitespace')],
                      parse_search_terms('   extraneous      whitespace '))
Example #2
0
 def test_words(self):
     # search strings with single words
     self.assertEqual([(None, 'word')], parse_search_terms('word'))
     self.assertEqual([(None, 'multiple'), (None, 'words')],
                      parse_search_terms('multiple words'))
     self.assertEqual([(None, 'extraneous'), (None, 'whitespace')],
                      parse_search_terms('   extraneous      whitespace '))
    def test_fields(self):
        self.assertEqual([('title', 'willows')],
                         parse_search_terms('title:willows'))

        self.assertEqual([('title', 'willows'), ('title', 'wind')],
                         parse_search_terms('title:willows title:wind'))

        self.assertEqual([(None, 'frog'), (None, 'toad'), ('title', 'willows'),
                          ('title', 'wind')],
                         parse_search_terms('frog toad title:willows title:wind'))
Example #4
0
    def test_fields(self):
        self.assertEqual([('title', 'willows')],
                         parse_search_terms('title:willows'))

        self.assertEqual([('title', 'willows'), ('title', 'wind')],
                         parse_search_terms('title:willows title:wind'))

        self.assertEqual(
            [(None, 'frog'), (None, 'toad'), ('title', 'willows'),
             ('title', 'wind')],
            parse_search_terms('frog toad title:willows title:wind'))
Example #5
0
 def to_python(self, value):
     if not value:
         return []
     else:
         try:
             return parse_search_terms(value)
         except Exception:
              raise forms.ValidationError('There was an error parsing your search: %s' \
                                          % value)
Example #6
0
 def to_python(self, value):
     if not value:
         return []
     else:
         try:
             return parse_search_terms(value)
         except Exception:
             raise forms.ValidationError('There was an error parsing your search: %s' \
                                         % value)
 def test_phrases(self):
     # quoted phrases
     self.assertEqual([(None, 'exact phrase')],
                      parse_search_terms('"exact phrase"'))
Example #8
0
def keyword_search_suggest(request):
    '''Suggest helper for keyword search.  If the search string ends
    with a recognized field name with an optional value,
    e.g. ``user:`` or ``user:A``, looks up existing values using Solr
    facets.  Returns a JSON response with the 15 most common matching
    terms in the requested field with the search term prefix, if any.
    If the search string is empty or ends with a space, suggests
    available search fields with an explanation.

    .. Note::

        Due to the current implementation and the limitations of facet
        querying in Solr, the search term is case-sensitive and only
        matches at the beginning of the string.

    Return format is suitable for use with `JQuery UI Autocomplete`_
    widget.

    .. _JQuery UI Autocomplete: http://jqueryui.com/demos/autocomplete/

    :param request: the http request passed to the original view
        method (used to retrieve the search term)
    '''
    term = request.GET.get('term', '')

    suggestions = []

    # if term is empty or ends in a space, suggest available search fields
    if term == '' or term[-1] == ' ':
        suggestions = [
            {'label': field,
             'value': '%s%s' % (term, field),
             'category': 'Search Fields',
             'desc': desc}
            for field, desc in KeywordSearch.field_descriptions.iteritems()
        ]

    # otherwise, check if there is a field to look up values for
    else:

        term_prefix, sep, term_suffix = term.rpartition(' ')
        value_prefix = term_prefix + sep
        # parse the last search term
        try:
            # parse could error in some cases
            parsed_terms = parse_search_terms(term_suffix)
            field, prefix = parsed_terms[-1]
        except Exception:
            field, prefix = None, ''

        if prefix is None:
            prefix = ''

        # if field can be faceted, suggest terms
        if field in KeywordSearch.facet_fields.keys():
            facet_field = KeywordSearch.facet_fields[field]

            # date created is a special case
            if field == 'created':
                sort = 'index'
                category = 'Date Added'

                # if less than 4 characters, suggest year
                if len(prefix) < 4:
                    facet_field = 'created_year'
                    result_fmt = '%s'
                # between 4 and 7, suggest year-month
                elif len(prefix) < 7:
                    facet_field = 'created_month'
                    result_fmt = '%s'
                # suggest full dates
                else:
                    result_fmt = '%s '

            elif field in ['added_by', 'user']:  # added_by or user
                sort = 'count'
                category = 'Users'
                result_fmt = '"%s" '


            # collection label
            if field == 'coll':
                sort = 'count'
                category = 'Collection'
                result_fmt = '%s '

                # if the term is numeric facet by source_id
                if prefix and prefix.isdigit():
                    facet_field = 'collection_source_id'

            solr = solr_interface()
            facetq = solr.query().paginate(rows=0)
            # filter by current user permssions
            # facetq = filter_by_perms(facetq, request.user)
            # return the 15 most common terms in the requested facet field
            # with a specified prefix
            facetq = facetq.facet_by(facet_field, prefix=prefix,
                                     sort=sort, limit=15)
            facets = facetq.execute().facet_counts.facet_fields

            # generate a dictionary to return via json with label (facet value
            # + count), and actual value to use
            suggestions = [{'label': '%s (%d)' % (facet, count),
                            'value': '%s%s:' % (value_prefix, field) + \
                                            result_fmt % facet,
                            'category': category}
                           for facet, count in facets[facet_field]
                           ]

    return HttpResponse(json_serializer.encode(suggestions),
                         content_type='application/json')
Example #9
0
 def test_phrases(self):
     # quoted phrases
     self.assertEqual([(None, 'exact phrase')],
                      parse_search_terms('"exact phrase"'))