module ElasticMapper::Search::ClassMethods

Public Instance Methods

Private Instance Methods

ordered_results(ids) click to toggle source

Fetch a set of ActiveRecord resources, looking up by the id returned by ElasticSearch. Maintain ElasticSearch's ordering.

@param ids [Array] array of ordered ids. @return results [Array] ActiveModel result set.

# File lib/elastic_mapper/search.rb, line 105
def ordered_results(ids)
  model_lookup = self.find(ids).inject({}) do |h, m|
    h[m.id] = m
    h
  end

  ids.map { |id| model_lookup[id] }
end
ordered_results_multi(ids_hash) click to toggle source

Note: the multi-search functionality kicks along a type value which is used to perform lookups on the appropriate underlying model.

# File lib/elastic_mapper/search.rb, line 118
def ordered_results_multi(ids_hash)
  model_lookup = self.find(ids_hash)
  ids_hash.map { |id_hash| model_lookup[id_hash[:id]] }
end
query_string_to_hash(query_string) click to toggle source

Create a query hash from a query string.

@param query_string [String] the string query. @return query_hash [Hash] query hash.

# File lib/elastic_mapper/search.rb, line 85
def query_string_to_hash(query_string)
  {
    "bool" => {
      "must" => [
        # This pattern is here for reference, it's useful
        # when it comes time to add multi-tenant support.
        # {"term" => {"user_id" => id}},
        { "query_string" => { "query" => query_string } }
      ]
    }
  }
end
sanitize_query(str) click to toggle source

sanitize a search query for Lucene. Useful if the original query raises an exception due to invalid DSL parse.

stackoverflow.com/questions/16205341/symbols-in-query-string-for-elasticsearch

@param str [String] the query string to sanitize.

# File lib/elastic_mapper/search.rb, line 130
def sanitize_query(str)
  # Escape special characters
  # http://lucene.apache.org/core/old_versioned_docs/versions/2_9_1/queryparsersyntax.html#Escaping Special Characters
  escaped_characters = Regexp.escape('\\+-&|!(){}[]^~*?:\/')
  str = str.gsub(/([#{escaped_characters}])/, '\\\\\1')

  # AND, OR and NOT are used by lucene as logical operators. We need
  # to escape them
  ['AND', 'OR', 'NOT'].each do |word|
    escaped_word = word.split('').map {|char| "\\#{char}" }.join('')
    str = str.gsub(/\s*\b(#{word.upcase})\b\s*/, " #{escaped_word} ")
  end

  # Escape odd quotes
  quote_count = str.count '"'
  str = str.gsub(/(.*)"(.*)/, '\1\"\3') if quote_count % 2 == 1

  str
end