Дата актуализации: .
При работе с Elasticsearch часто возникает необходимость искать документы, содержащие слова, которые одновременно являются зарезервированными символами или ключевыми словами языка запросов (например, AND, OR, NOT, +, -, !, ~, *, ?, :, , /, (, ), {, }, [, ], "). Если такие слова встречаются в индексируемом тексте как обычные термины, их нужно искать точно так же, как и любые другие слова, но без учёта их специального значения в синтаксисе запроса. Для этого применяются кавычки («» или “”) – они переводят содержимое в фразовый запрос и отключают обработку зарезервированных символов.
Почему кавычки важны?
- Отключение синтаксиса query_string. Внутри двойных кавычек Elasticsearch воспринимает всё как одну фразу и не пытается разбирать её на операторы.
- Точное совпадение. Кавычки гарантируют, что будет найден документ, содержащий именно эту последовательность токенов в том же порядке.
- Поддержка регистронезависимого поиска. При использовании стандартных анализаторов (например,
standardилиrussian) внутри кавычек всё равно применяется токенизация и фильтрация, поэтому поиск остаётся нечувствительным к регистру и к stemming.
Основные способы экранирования зарезервированных слов
Query String с двойными кавычками
Самый простой способ – использовать запрос типа query_string и заключить искомое слово в двойные кавычки.
GET /my_index/_search
{
"query": {
"query_string": {
"query": ""AND"",
"default_field": "name"
}
}
}
В данном примере будет найден любой документ, поле name которого содержит токен and (после применения анализатора russian или standard он будет приведён к нижнему регистру).
Match Phrase
Если вам не нужен полный синтаксис query_string, можно воспользоваться запросом match_phrase. Он также обрабатывает фразу как единое целое и не требует экранирования специальных символов.
GET /my_index/_search
{
"query": {
"match_phrase": {
"name": "AND"
}
}
}
Term‑level запрос (keyword поле)
Когда поле объявлено как keyword (не анализируется), достаточно точного совпадения без кавычек, но если в значении присутствуют зарезервированные символы, их всё же нужно экранировать в самом значении:
GET /my_index/_search
{
"query": {
"term": {
"name.raw": ""AND""
}
}
}
Здесь мы ищем точное значение "AND" (включая кавычки) в неанализированном поле name.raw. Если нужно найти слово без кавычек, просто указываем AND.
Примеры с русским анализатором
Допустим, у нас есть индекс test_search с маппингом из вопроса:
PUT /test_search
{
"mappings": {
"first_test": {
"properties": {
"number": { "type": "keyword" },
"name": {
"type": "text",
"analyzer": "russian",
"fields": {
"raw": { "type": "keyword" }
}
}
}
}
}
}
Индексируем несколько документов:
POST /test_search/first_test/_bulk
{ "index": { "_id": 1 } }
{ "name": "В этом документе есть слово AND" }
{ "index": { "_id": 2 } }
{ "name": "Здесь AND используется как оператор" }
{ "index": { "_id": 3 } }
{ "name": "Нет такого слова" }
Поиск зарезервированного слова AND
GET /test_search/first_test/_search
{
"query": {
"query_string": {
"query": ""AND"",
"default_field": "name"
} }
}
Результат: документы с _id 1 и 2, потому что оба содержат токен and после применения русского анализатора (приведение к нижнему регистру, удаление стоп‑слов не затрагивает and).
Поиск фразы с несколькими зарезервированными словами
Нужно найти документы, где встречается фраза AND OR NOT:
GET /test_search/first_test/_search
{
"query": {
"match_phrase": {
"name": "AND OR NOT"
}
}
}
Если таких документов нет, запрос вернёт пустой результат.
Частые ошибки и как их избегать
- Забывание про регистр. В
query_stringвнутри кавычек регистр всё равно нормализуется анализатором. Если вы используетеkeywordполе без анализатора, то"And"и"and"будут различаться. - Экранирование обратным слешем вместо кавычек. Обратный слеш () экранирует отдельный символ, но не отменяет синтаксис операторов. Для полного отключения нужны кавычки.
- Использование одинарных кавычек. В Elasticsearch одинарные кавычки не имеют специального значения в query_string; они воспринимаются как обычные символы. Поэтому для фразового поиска нужны именно двойные кавычки.
- Смешивание анализируемых и неанализируемых полей. Если вы ищете в
keywordполе, но всё равно ставите кавычки, ищите буквально кавычки как часть термина. Убедитесь, что выбран правильный тип поля.
Рекомендации по использованию
- Для полнотекстового поиска зарезервированных слов предпочтительно использовать
match_phraseилиquery_stringс двойными кавычками. - Если поле не анализируется (
keyword) и вам нужно точное совпадение, используйтеtermбез кавычек (или с кавычками, если они действительно часть значения). - При составлении сложных булевых выражений выносите зарезервированные слова в отдельные
query_string‑подзапросы, заключая каждое в кавычки, чтобы избежать неоднозначности. - Тестируйте запросы через
_analyzeAPI, чтобы увидеть, как анализатор преобразует ваш запрос:
GET /test_search/_analyze
{
"analyzer": "russian",
"text": ""AND""
}
Вы увидите, что токен and производится без кавычек, подтверждая, что кавычки работают как группирующий оператор.
Кавычки в Elasticsearch – простой и надёжный способ искать зарезервированные слова и символы, лишая их специального значения в синтаксисе запросов; Независимо от того, используете ли вы полнотекстовый (match_phrase, query_string) или терм‑уровневый (term) поиск, правильное применение кавычек гарантирует, что вы получите именно те документы, которые содержат нужный термин в точном виде, независимо от его служебного значения в языке запросов.
Помните: всегда проверяйте, как ваш запрос преобразуется анализатором (через _analyze), и тестируйте на небольшом наборе данных перед запуском в production. Это избавит от неприятных сюрпризов и сделает ваш поиск предсказуемым и эффективным.