Запрос Elasticsearch Bool с параметром minimum_should_match, равным нулю, не выполняется

#elasticsearch #elastic-stack #elk #booleanquery

Вопрос:

Я добавляю 3 документа

 POST test/_doc
{"value": 1}

POST test/_doc
{"value": 2}

POST test/_doc
{"value": 3}
 

затем сделайте следующий запрос, я ожидаю, что верну все 3 документа с предложением «соответствие документам должно быть оценено выше».

 GET /test/_search
{
  "query": {
    "bool": {
      "minimum_should_match": 0,
      "should": [
        {
          "range": {
            "value": {
              "gte": 2
            }
          }
        }
      ]
    }
  }
}
 

но вместо этого я получаю только 2 документа (значение 2,3) "minimum_should_match": 0, , которые не имеют никакого эффекта, пока я не добавлю filter must предложение or в запрос bool, как показано ниже,

 GET /test/_search
{
  "query": {
    "bool": {
       "filter": [ { "match_all": { } } ],
      "should": [
        {
          "range": {
            "value": {
              "gte": 2
            }
          }
        }
      ]
    }
  }
}
 

Чего я хочу

в запросе bool либо предложение must, либо предложение filter пусто или заполнено, предложение should не должно фильтровать какие-либо документы, а только участвовать в ранжировании, пожалуйста, поделитесь, как я могу этого достичь, спасибо

Ответ №1:

Немного странно, что minimum_should_match: 0 это не работает с should этим пунктом. Это может быть связано с документацией, упомянутой здесь

Независимо от того, к какому числу приводит расчет, значение, большее числа необязательных предложений, или значение, меньшее 1, никогда не будет использоваться. (т. е.: независимо от того, насколько низок или высок результат вычисления, минимальное количество требуемых совпадений никогда не будет меньше 1 или больше, чем количество предложений.

Существует два способа, с помощью которых вы можете получить все документы в результате, и использование should предложения только для целей ранжирования

  1. Используйте must filter предложение или с match_all запросом, с которым вы уже разобрались, как показано в вопросе выше.
  2. Другим способом может быть использование should предложения с boost параметром

Поисковый запрос:

 {
  "query": {
    "bool": {
      "should": [
        {
          "range": {
            "value": {
              "gte": 2,
              "boost": 2.0
            }
          }
        },
        {
          "range": {
            "value": {
              "lt": 2,
              "boost": 1.0
            }
          }
        }
      ]
    }
  }
}
   
 

Результатом поиска будет

 "hits": [
      {
        "_index": "68040640",
        "_type": "_doc",
        "_id": "2",
        "_score": 2.0,
        "_source": {
          "value": 2
        }
      },
      {
        "_index": "68040640",
        "_type": "_doc",
        "_id": "3",
        "_score": 2.0,
        "_source": {
          "value": 3
        }
      },
      {
        "_index": "68040640",
        "_type": "_doc",
        "_id": "1",
        "_score": 1.0,
        "_source": {
          "value": 1
        }
      }
    ]
 

Комментарии:

1. @Kamboh у вас была возможность ознакомиться с ответом, с нетерпением жду ваших отзывов 🙂