0

I am trying to match the title of a product listing to a database of known products. My first idea was to put the known products and their metadata into elasticsearch and try to find the best match with multi_match. My current query is something like:

{
  "query": {
    "multi_match" : {
      "query": "Men's small blue cotton pants SKU123", 
      "fields": ["sku^2","title","gender","color", "material","size"],
      "type" : "cross_fields"
    }
  }
}

The problem is sometimes it will return products with the wrong color. Is there a way i could modify the above query to only score items in my index that have a color field equal to a word that exists in the query string? I am using elasticsearch 5.1.

rdelbel
  • 73
  • 4

1 Answers1

1

If you want elasticsearch to score only items that meet certain criteria then you need to use the terms query in a filter context. Since the terms query does not analyze your query, you'll have to do that yourself. Something simple would be to tokenize by whitespace and lowercase and generate a query that looks like this:

{
  "query": {
    "bool": {
      "filter": {
        "terms": {
          "color": ["men's", "small", "blue", "cotton", "pants", "sku123"]
        }
      },
      "must": {
        "multi_match": {
          "query": "Men's small blue cotton pants SKU123",
          "fields": [
            "sku^2",
            "title",
            "gender",
            "material",
            "size"
          ],
          "type": "cross_fields"
        }
      }
    }
  }
}
Alkis Kalogeris
  • 17,044
  • 15
  • 59
  • 113
  • Thank you for the quick response. After some testing this code works when the color is only one word like "blue" however it seems like the above query will also match items in the index that have multi word colors such as "light blue" or "dark blue". Is there a way to only surface the items that have all words in the color field exist in the keyword? (They could be out of order or non contiguous) – rdelbel Feb 06 '17 at 17:27
  • I don't believe this is possible. You can have a query to match all the query tokens, but not the other way around. More importantly though, do you really need this? I mean if I was a user, then when I ask for blue I would want light blue in the results. A similar question has been asked before http://stackoverflow.com/questions/32580295/elasticsearch-match-all-words-from-document-in-the-search-query. Basically you can use this query and do what you want on application level. – Alkis Kalogeris Feb 06 '17 at 18:55
  • Of course you can always use scripting to achieve something out of the ordinary, but I advise caution. It can have a significant overhead. – Alkis Kalogeris Feb 06 '17 at 19:03