Эластичный поисковый запрос не возвращает результаты

У меня есть запрос эластичного поиска, который не возвращает данные. Вот 2 примера запроса - первый работает и возвращает несколько записей, а второй ничего не возвращает - что мне не хватает?

Пример 1 работает:

curl -X GET "localhost:9200/_search?pretty" -H 'Content-Type: application/json' -d'
{
  "query": {
    "match": {
      "data.case.field1": "ABC123"
    }
  }
}
'

Пример 2 не работает:

curl -X GET "localhost:9200/_search?pretty" -H 'Content-Type: application/json' -d'
{
  "query": {
    "bool": {
      "must": {
        "term" : { "data.case.field1" : "ABC123" }
      }
    }
  }
}
'

3 ответа

Решение

Это происходит из-за разницы между match и term запросы, matchзапросы анализируются, что означает, что к поисковому запросу применен тот же анализатор, который используется в поле во время индексации, а term запросы не анализируются и не используются для точного поиска, и search termin term запросы не проходят процесс анализа.

Официальный документ запроса термина

Возвращает документы, содержащие точный термин в указанном поле.

Официальный документ запроса соответствия

Возвращает документы, соответствующие указанному тексту, числу, дате или логическому значению. Предоставленный текст анализируется перед сопоставлением.

Если вы используете текстовое поле для data.case.field1 без какого-либо явного анализатора, чем будет применен анализатор по умолчанию (стандартный) для текстового поля, который строчные буквы текста и сохранит результирующий токен.

Для вашего текста стандартный анализатор выдаст токен, указанный ниже. Дополнительные сведения см. В Analyze API.

{
    "text" : "ABC123",
    "analyzer" : "standard"
}

И сгенерированный токен

{
    "tokens": [
        {
            "token": "abc123",
            "start_offset": 0,
            "end_offset": 6,
            "type": "<ALPHANUM>",
            "position": 0
        }
    ]
}

Теперь, когда вы используете term запрос как поисковый запрос не будет анализироваться и использоваться как есть, который в captical char(ABC123) не соответствует токенам в индексе, следовательно, не возвращает результат.

PS: обратитесь к моему этому SO-ответу для получения более подробной информации о запросах на поиск и совпадение.

Для чего нужна ваша карта data.case.field1? Если это текст типа, вы должны использовать запрос на совпадение вместо термина.

См. Предупреждение вверху этой страницы: https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-term-query.html#query-dsl-term-query

Если мы не знаем тип сопоставления как text или же keyword. Он относительно отвечает в темноте, не зная всех задействованных переменных. Может быть, вы можете попробовать следующее.

curl -X GET "localhost:9200/_search?pretty" -H 'Content-Type: application/json' -d'
{
  "query": {
    "bool": {
      "filter": { <- Try this if you have datatype as keyword
        "term" : { "data.case.field1" : "ABC123" }
      }
    }
  }
}

'

Другие вопросы по тегам