Эластичный поисковый запрос не возвращает результаты
У меня есть запрос эластичного поиска, который не возвращает данные. Вот 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 term
in 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" }
}
}
}
}
'