Spec-Zone.ru › Elasticsearch 8
›Руководство по Elasticsearch [8.17] ›DSL-запросы ›Запросы по полному тексту

Запрос по строке поиска

На этой странице приведена информация о типе запроса query_string. Информацию о выполнении поискового запроса в Elasticsearch см. в API поиска.

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

Этот запрос использует синтаксис для парсинга и разделения предоставленной строки поиска на основе операторов, таких как AND или NOT. Затем запрос анализирует каждый разделенный текст независимо перед возвращением соответствующих документов.

Вы можете использовать запрос query_string для создания сложного поиска, включающего символы подстановки, поиск по нескольким полям и многое другое. Несмотря на универсальность, запрос строгий и возвращает ошибку, если строка запроса содержит некорректный синтаксис.

Поскольку он возвращает ошибку для любого некорректного синтаксиса, мы не рекомендуем использовать запрос query_string для поисковых полей.

Если вам не нужно поддерживать синтаксис запроса, рассмотрите использование запроса match. Если вам необходимы возможности синтаксиса запроса, используйте запрос simple_query_string, который менее строгий.

Пример запроса

При выполнении следующего поиска запрос query_string разделяет (new york city) OR (big apple) на две части: new york city и big apple. Затем анализатор поля content независимо преобразует каждую часть в токены перед возвращением соответствующих документов. Поскольку синтаксис запроса не использует пробелы в качестве оператора, new york city передается анализатору как есть.

resp = client.search(
    query={
        "query_string": {
            "query": "(new york city) OR (big apple)",
            "default_field": "content"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        query: '(new york city) OR (big apple)',
        default_field: 'content'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "query": "(new york city) OR (big apple)",
	      "default_field": "content"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      query: "(new york city) OR (big apple)",
      default_field: "content",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "query": "(new york city) OR (big apple)",
      "default_field": "content"
    }
  }
}

Параметры верхнего уровня для query_string

query
(Обязательный, строка) Строка запроса, которую вы хотите обработать и использовать для поиска. См. синтаксис строки запроса.
default_field

(Необязательный, строка) Поле по умолчанию для поиска, если в строке запроса не указано поле. Поддерживает подстановки (*).

По умолчанию используется значение из index.query.default_field настроек индекса, которое имеет значение по умолчанию *. Значение * извлекает все поля, подходящие для запросов по терминам, и фильтрует поля метаданных. Все извлеченные поля затем объединяются для построения запроса, если не указан параметр prefix.

Поиск по всем подходящим полям не включает вложенные документы. Используйте nested запрос для поиска этих документов.

Для индексов с большим количеством полей поиск по всем подходящим полям может быть ресурсоёмким.

Существует ограничение на количество полей и терминов, которые могут быть запрошены одновременно. Оно определяется настройкой indices.query.bool.max_clause_count настроек поиска.

allow_leading_wildcard
(Необязательный, логический) Если true, символы подстановки * и ? разрешены в качестве первого символа строки запроса. По умолчанию true.
analyze_wildcard
(Необязательный, логический) Если true, запрос пытается проанализировать термин-подстановку в строке запроса. По умолчанию false.
analyzer
(Необязательный, строка) Анализатор, используемый для преобразования текста в строке запроса в токены. По умолчанию используется анализатор индекса, сопоставленный для поля default_field. Если анализатор не сопоставлен, используется анализатор по умолчанию для индекса.
auto_generate_synonyms_phrase_query
(Необязательный, логический) Если true, автоматически создаются запросы match phrase для многословных синонимов. По умолчанию true. См. Синонимы и запрос query_string для примера.
boost

(Необязательный, число с плавающей точкой) Число с плавающей точкой, используемое для уменьшения или увеличения оценок релевантности запроса. По умолчанию 1.0.

Значения буста относительны к значению по умолчанию 1.0. Значение буста между 0 и 1.0 уменьшает оценку релевантности. Значение больше, чем 1.0, увеличивает оценку релевантности.

default_operator

(Необязательный, строка) Логика по умолчанию для интерпретации текста в строке запроса, если операторы не указаны. Допустимые значения:

OR (По умолчанию)
Например, строка запроса capital of Hungary интерпретируется как capital OR of OR Hungary.
AND
Например, строка запроса capital of Hungary интерпретируется как capital AND of AND Hungary.
enable_position_increments
(Необязательный, логический) Если true, включить приращения позиции в запросах, построенных из поиска query_string. По умолчанию true.
fields

(Необязательный, массив строк) Массив полей для поиска. Поддерживает подстановки (*).

Вы можете использовать этот параметр для поиска по нескольким полям. См. Поиск по нескольким полям.

fuzziness
(Необязательный, строка) Максимальное расстояние редактирования, разрешенное для неточного соответствия. Для неточного синтаксиса см. Неточность.
fuzzy_max_expansions
(Необязательный, целое число) Максимальное количество терминов, до которых расширяется запрос для неточного соответствия. По умолчанию 50.
fuzzy_prefix_length
(Необязательный, целое число) Максимальное количество начальных символов, оставленных неизменными для неточного соответствия. По умолчанию 0.
fuzzy_transpositions
(Необязательный, логический) Если true, правки для неточного соответствия включают перестановки двух смежных символов (ab → ba). По умолчанию true.
lenient
(Необязательный, логический) Если true, ошибки, основанные на формате, такие как предоставление текстового значения для поля типа числовой, игнорируются. По умолчанию false.
max_determinized_states

(Необязательный, целое число) Максимальное количество состояний автомата, необходимых для запроса. По умолчанию 10000.

Elasticsearch использует Apache Lucene для обработки регулярных выражений. Lucene преобразует каждое регулярное выражение в конечный автомат, содержащий определенное количество детерминированных состояний.

Вы можете использовать этот параметр, чтобы предотвратить нежелательное потребление ресурсов при преобразовании сложных регулярных выражений.

minimum_should_match
(Необязательный, строка) Минимальное количество клаузов, которые должны соответствовать для возврата документа. См. minimum_should_match параметр для допустимых значений и дополнительной информации. См. Как работает minimum_should_match для примера.
quote_analyzer

(Необязательный, строка) Анализатор, используемый для преобразования цитируемого текста в строке запроса в токены. По умолчанию используется search_quote_analyzer для поля default_field.

Для цитируемого текста этот параметр переопределяет анализатор, указанный в параметре analyzer.

phrase_slop
(Необязательный, целое число) Максимальное количество позиций, разрешенных между соответствующими токенами для фраз. По умолчанию 0. Если 0, требуется точное совпадение фразы. Для переставленных терминов значение параметра slop равно 2.
quote_field_suffix

(Необязательный, строка) Суффикс, добавляемый к цитируемому тексту в строке запроса.

Вы можете использовать этот суффикс, чтобы использовать другой метод анализа для точных совпадений. См. Смешивание точного поиска со стеммингом.

rewrite
(Необязательный, строка) Метод переработки запроса. Для допустимых значений и дополнительной информации см. rewrite параметр.
time_zone

(Необязательный, строка) Смещение Coordinated Universal Time (UTC) или часовой пояс IANA, используемый для преобразования значений date в строке запроса в UTC.

Допустимые значения — смещения UTC в формате ISO 8601, например, +01:00 или -08:00, и идентификаторы часовых поясов IANA, такие как America/Los_Angeles.

Параметр time_zone не влияет на значение date math now. now всегда представляет текущее время в UTC. Однако параметр time_zone преобразует даты, рассчитанные с помощью now и округления date math. Например, параметр time_zone преобразует значение now/d.

Примечания

Синтаксис строки запроса

Язык строки запроса используется запросом по строке и параметром строки запроса q в search API.

Строка запроса разбирается на ряд терминов и операторов. Термин может быть одним словом — quick или brown — или фразой, заключённой в двойные кавычки — "quick brown" — которая ищет все слова в фразе в том же порядке.

Операторы позволяют настроить поиск — доступные варианты описаны ниже.

Имена полей

Вы можете указать поля для поиска в синтаксисе запроса:

  • где поле status содержит active

    status:active
  • где поле title содержит quick или brown

    title:(quick OR brown)
  • где поле author содержит точную фразу "john smith"

    author:"John Smith"
  • где поле first name содержит Alice (обратите внимание, как нам нужно экранировать пробел с помощью обратного слэша)

    first\ name:Alice
  • где любое из полей book.title, book.content или book.date содержит quick или brown (обратите внимание, как нам нужно экранировать * с помощью обратного слэша):

    book.\*:(quick OR brown)
  • где поле title имеет любое непустое значение:

    _exists_:title
Подстановочные знаки

Поиск с подстановочными знаками может выполняться по отдельным терминам, используя ? для замены одного символа и * для замены нуля или более символов:

qu?ck bro*

Помните, что запросы с подстановочными знаками могут использовать огромное количество памяти и работать очень медленно — просто представьте, сколько терминов нужно запросить для соответствия строке запроса "a* b* c*".

Чистые подстановочные знаки \* переписываются в запросы exists для повышения эффективности. Вследствие этого, подстановочный знак "field:*" будет соответствовать документам с пустым значением, например:

{
  "field": ""
}

... и не будет соответствовать, если поле отсутствует или задано явным значением null, например:

{
  "field": null
}

Разрешение подстановочного знака в начале слова (например, "*ing") является особенно ресурсоёмким, поскольку все термины в индексе необходимо проверить, чтобы убедиться, что они соответствуют. Разрешение ведущих подстановочных знаков может быть отключено путем установки allow_leading_wildcard в значение false.

Применяются только части цепочки анализа, которые работают на уровне символов. Таким образом, например, если анализатор выполняет как приведение к нижнему регистру, так и стеминг, будет применено только приведение к нижнему регистру: применение стеминга к слову, у которого отсутствуют некоторые буквы, будет неправильным.

Установив analyze_wildcard в значение true, запросы, заканчивающиеся на *, будут проанализированы, и из различных токенов будет построен булев запрос, гарантируя точное соответствие первым N-1 токенам и соответствие префиксом последнему токену.

Регулярные выражения

Шаблоны регулярных выражений можно встраивать в строку запроса, заключая их в обратные слэши ("/"):

name:/joh?n(ath[oa]n)/

Поддерживаемый синтаксис регулярных выражений описан в синтаксисе регулярных выражений.

Параметр allow_leading_wildcard не имеет никакого контроля над регулярными выражениями. Запрос по строке, например, следующий, заставит Elasticsearch посетить каждый термин в индексе:

/.*n/

Используйте с осторожностью!

Неточность

Вы можете выполнить запросы с неточностью с помощью оператора ~:

quikc~ brwn~ foks~

Для этих запросов строка запроса нормализуется. При необходимости применяются только определенные фильтры из анализатора. Список применимых фильтров см. в нормализаторах.

Запрос использует расстояние Дамерау-Левенштейна, чтобы найти все термины с максимальным числом двух изменений, где изменение — это вставка, удаление или замена одного символа или перестановка двух смежных символов.

По умолчанию расстояние редактирования равно 2, но расстояние редактирования 1 должно быть достаточно, чтобы уловить 80% всех опечаток человека. Его можно указать следующим образом:

quikc~1

Избегайте смешивания неточности с подстановочными знаками

Смешивание неточности и подстановочных знаков не поддерживается. При смешивании один из операторов не применяется. Например, вы можете искать app~1 (с неточностью) или app* (с подстановочными знаками), но поиск app*~1 не применяет оператор неточности (~1).

Поиск вблизи

В то время как фразовый запрос (например, "john smith") ожидает, что все термины будут в точно в том же порядке, запрос на близость позволяет указанным словам быть более удалёнными или в другом порядке. Так же, как запросы с неточностью могут указать максимальное расстояние редактирования для символов в слове, поиск вблизи позволяет указать максимальное расстояние редактирования слов во фразе:

"fox quick"~5

Чем ближе текст в поле к исходному порядку, указанному в строке запроса, тем более релевантным считается этот документ. По сравнению с вышеприведённым примером запроса, фраза "quick fox" будет считаться более релевантной, чем "quick brown fox".

Диапазоны

Диапазоны могут быть заданы для полей даты, числовых или строковых значений. Включительно диапазоны задаются в квадратных скобках [min TO max], а исключительные диапазоны — в фигурных скобках {min TO max}.

  • Все дни 2012 года:

    date:[2012-01-01 TO 2012-12-31]
  • Числа 1..5

    count:[1 TO 5]
  • Теги между alpha и omega, исключая alpha и omega:

    tag:{alpha TO omega}
  • Числа от 10 и выше

    count:[10 TO *]
  • Даты до 2012 года

    date:{* TO 2012-01-01}

Фигурные и квадратные скобки можно комбинировать:

  • Числа от 1 до, но не включая 5

    count:[1 TO 5}

Диапазоны с одной неограниченной стороной могут использовать следующий синтаксис:

age:>10
age:>=10
age:<10
age:<=10

Для объединения верхней и нижней границы с упрощённым синтаксисом необходимо объединить два условия с оператором AND:

age:(>=10 AND <20)
age:(+>=10 +<20)

Разбор диапазонов в строках запросов может быть сложным и подвержен ошибкам. Гораздо надёжнее использовать явный range запрос.

Усиление

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

quick^2 fox

Значение по умолчанию boost равно 1, но может быть любым положительным числом с плавающей запятой. Усиления между 0 и 1 уменьшают релевантность.

Усиления также могут применяться к фразам или группам:

"john smith"^2   (foo bar)^4
Булевы операторы

По умолчанию все термины являются необязательными, пока хотя бы один термин совпадает. Поиск foo bar baz найдёт любой документ, содержащий один или несколько из foo или bar или baz. Мы уже обсуждали default_operator выше, который позволяет сделать все термины обязательными, но также существуют булевы операторы, которые можно использовать в строке запроса для большего контроля.

Предпочтительные операторы — + (этот термин обязательно должен присутствовать) и - (этот термин обязательно не должен присутствовать). Все остальные термины необязательны. Например, этот запрос:

quick brown +fox -news

означает:

  • fox должен присутствовать
  • news не должен присутствовать
  • quick и brown необязательны — их наличие увеличивает релевантность

Обычные булевы операторы AND, OR и NOT (также записываются как &&, || и !) также поддерживаются, но имейте в виду, что они не соблюдают обычные правила приоритета, поэтому скобки следует использовать при совместном применении нескольких операторов. Например, предыдущий запрос можно переписать как:

((quick AND fox) OR (brown AND fox) OR fox) AND NOT news
Эта форма теперь правильно воспроизводит логику из исходного запроса, но оценка релевантности мало похожа на исходную.

В отличие от этого, тот же запрос, переписанный с помощью match запроса, будет выглядеть так:

{
    "bool": {
        "must":     { "match": "fox"         },
        "should":   { "match": "quick brown" },
        "must_not": { "match": "news"        }
    }
}
Группировка

Несколько терминов или предложений могут быть сгруппированы вместе с помощью скобок для формирования подзапросов:

(quick OR brown) AND fox

Группы могут быть использованы для указания конкретного поля или для повышения результата подзапроса:

status:(active OR pending) title:(full text search)^2
Зарезервированные символы

Если вам нужно использовать любой символ, который функционирует как оператор в вашем запросе (а не как оператор), то его следует экранировать ведущей обратной косой чертой. Например, чтобы найти (1+1)=2, вам нужно написать запрос как \(1\+1\)\=2. При использовании JSON для тела запроса требуются две предшествующие обратные косые черты (\\); обратная косая черта — зарезервированный символ экранирования в JSON-строках.

resp = client.search(
    index="my-index-000001",
    query={
        "query_string": {
            "query": "kimchy\\!",
            "fields": [
                "user.id"
            ]
        }
    },
)
print(resp)
response = client.search(
  index: 'my-index-000001',
  body: {
    query: {
      query_string: {
        query: 'kimchy\\!',
        fields: [
          'user.id'
        ]
      }
    }
  }
)
puts response
const response = await client.search({
  index: "my-index-000001",
  query: {
    query_string: {
      query: "kimchy\\!",
      fields: ["user.id"],
    },
  },
});
console.log(response);
GET /my-index-000001/_search
{
  "query" : {
    "query_string" : {
      "query" : "kimchy\\!",
      "fields"  : ["user.id"]
    }
  }
}

Зарезервированные символы: + - = && || > < ! ( ) { } [ ] ^ " ~ * ? : \ /

Неправильное экранирование этих специальных символов может привести к синтаксической ошибке, которая предотвратит выполнение запроса.

< и > вообще нельзя экранировать. Единственный способ предотвратить попытку создания запроса диапазона — полностью удалить их из строки запроса.

Пробелы и пустые запросы

Пробелы не рассматриваются как операторы.

Если строка запроса пуста или содержит только пробелы, запрос вернёт пустой результат.

Избегайте использования запроса query_string для вложенных документов

Поиски query_string не возвращают вложенные документы. Для поиска вложенных документов используйте nested запрос.

Поиск по нескольким полям

Вы можете использовать параметр fields для выполнения поиска query_string по нескольким полям.

Идея запуска query_string запроса по нескольким полям заключается в расширении каждого поискового термина до оператора OR так:

field1:query_term OR field2:query_term | ...

Например, следующий запрос

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "content",
                "name"
            ],
            "query": "this AND that"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'content',
          'name'
        ],
        query: 'this AND that'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "content",
	        "name"
	      ],
	      "query": "this AND that"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["content", "name"],
      query: "this AND that",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "fields": [ "content", "name" ],
      "query": "this AND that"
    }
  }
}

соответствует тем же словам, что и

resp = client.search(
    query={
        "query_string": {
            "query": "(content:this OR name:this) AND (content:that OR name:that)"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        query: '(content:this OR name:this) AND (content:that OR name:that)'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "query": "(content:this OR name:this) AND (content:that OR name:that)"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      query: "(content:this OR name:this) AND (content:that OR name:that)",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "query": "(content:this OR name:this) AND (content:that OR name:that)"
    }
  }
}

Поскольку несколько запросов генерируются из отдельных поисковых терминов, их объединение автоматически выполняется с помощью dis_max запроса с tie_breaker. Например (name усилен на 5 с помощью ^5):

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "content",
                "name^5"
            ],
            "query": "this AND that OR thus",
            "tie_breaker": 0
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'content',
          'name^5'
        ],
        query: 'this AND that OR thus',
        tie_breaker: 0
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "content",
	        "name^5"
	      ],
	      "query": "this AND that OR thus",
	      "tie_breaker": 0
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["content", "name^5"],
      query: "this AND that OR thus",
      tie_breaker: 0,
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string" : {
      "fields" : ["content", "name^5"],
      "query" : "this AND that OR thus",
      "tie_breaker" : 0
    }
  }
}

Простой символ подстановки также может использоваться для поиска «внутри» определённых внутренних элементов документа. Например, если у нас есть объект city с несколькими полями (или вложенным объектом с полями), мы можем автоматически искать по всем полям «город»:

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "city.*"
            ],
            "query": "this AND that OR thus"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'city.*'
        ],
        query: 'this AND that OR thus'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "city.*"
	      ],
	      "query": "this AND that OR thus"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["city.*"],
      query: "this AND that OR thus",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string" : {
      "fields" : ["city.*"],
      "query" : "this AND that OR thus"
    }
  }
}

Другой вариант — предоставить поиск по полям с подстановкой в строку запроса (надлежащим образом экранируя символ *), например: city.\*:something:

resp = client.search(
    query={
        "query_string": {
            "query": "city.\\*:(this AND that OR thus)"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        query: 'city.\\*:(this AND that OR thus)'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "query": "city.\\*:(this AND that OR thus)"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      query: "city.\\*:(this AND that OR thus)",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string" : {
      "query" : "city.\\*:(this AND that OR thus)"
    }
  }
}

Поскольку \ (обратная косая черта) — специальный символ в JSON-строках, он должен быть экранирован, поэтому в вышеприведённом query_string используются две обратные косые черты.

Параметр fields также может включать имена полей на основе шаблонов, позволяя автоматически расширить поиск до соответствующих полей (включая динамически введённые поля). Например:

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "content",
                "name.*^5"
            ],
            "query": "this AND that OR thus"
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'content',
          'name.*^5'
        ],
        query: 'this AND that OR thus'
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "content",
	        "name.*^5"
	      ],
	      "query": "this AND that OR thus"
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["content", "name.*^5"],
      query: "this AND that OR thus",
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string" : {
      "fields" : ["content", "name.*^5"],
      "query" : "this AND that OR thus"
    }
  }
}
Дополнительные параметры для поиска по нескольким полям

При выполнении запроса query_string по нескольким полям поддерживаются следующие дополнительные параметры.

type

(Необязательный, строка) Определяет, как запрос сопоставляет и оценивает документы. Допустимые значения:

best_fields (По умолчанию)
Находит документы, которые соответствуют любому полю и использует наивысший _score из любого соответствующего поля. См. best_fields.
bool_prefix
Создает запрос match_bool_prefix по каждому полю и комбинирует _score из каждого поля. См. bool_prefix.
cross_fields
Обрабатывает поля с одинаковым analyzer как одно большое поле. Ищет каждое слово в любом поле. См. cross_fields.
most_fields
Находит документы, которые соответствуют любому полю, и объединяет _score из каждого поля. См. most_fields.
phrase
Выполняет запрос match_phrase по каждому полю и использует _score из лучшего поля. См. phrase и phrase_prefix.
phrase_prefix
Выполняет запрос match_phrase_prefix по каждому полю и использует _score из лучшего поля. См. phrase и phrase_prefix.

ПРИМЕЧАНИЕ: Дополнительные параметры верхнего уровня multi_match могут быть доступны в зависимости от значения type.

Синонимы и запрос query_string

Запрос query_string поддерживает расширение синонимов по нескольким терминам с помощью фильтра токенов synonym_graph. При использовании этого фильтра анализатор создаёт фразовый запрос для каждого синонима по нескольким терминам. Например, следующий синоним: ny, new york даст:

(ny OR ("new york"))

Также можно сопоставить синонимы по нескольким терминам с помощью союзов:

$params = [
    'body' => [
        'query' => [
            'query_string' => [
                'default_field' => 'title',
                'query' => 'ny city',
                'auto_generate_synonyms_phrase_query' => false,
            ],
        ],
    ],
];
$response = $client->search($params);
resp = client.search(
    query={
        "query_string": {
            "default_field": "title",
            "query": "ny city",
            "auto_generate_synonyms_phrase_query": False
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        default_field: 'title',
        query: 'ny city',
        auto_generate_synonyms_phrase_query: false
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "default_field": "title",
	      "query": "ny city",
	      "auto_generate_synonyms_phrase_query": false
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      default_field: "title",
      query: "ny city",
      auto_generate_synonyms_phrase_query: false,
    },
  },
});
console.log(response);
GET /_search
{
   "query": {
       "query_string" : {
           "default_field": "title",
           "query" : "ny city",
           "auto_generate_synonyms_phrase_query" : false
       }
   }
}

Приведённый выше пример создаёт булевый запрос:

(ny OR (new AND york)) city

который соответствует документам с термином ny или союзом new AND york. По умолчанию параметр auto_generate_synonyms_phrase_query имеет значение true.

Как работает minimum_should_match

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

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "title"
            ],
            "query": "this that thus",
            "minimum_should_match": 2
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'title'
        ],
        query: 'this that thus',
        minimum_should_match: 2
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "title"
	      ],
	      "query": "this that thus",
	      "minimum_should_match": 2
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["title"],
      query: "this that thus",
      minimum_should_match: 2,
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "fields": [
        "title"
      ],
      "query": "this that thus",
      "minimum_should_match": 2
    }
  }
}

Приведённый выше пример создаёт булевый запрос:

(title:this title:that title:thus)~2

который соответствует документам как минимум с двумя из терминов this, that или thus в единственном поле title.

Как minimum_should_match работает для нескольких полей

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "title",
                "content"
            ],
            "query": "this that thus",
            "minimum_should_match": 2
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'title',
          'content'
        ],
        query: 'this that thus',
        minimum_should_match: 2
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "title",
	        "content"
	      ],
	      "query": "this that thus",
	      "minimum_should_match": 2
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["title", "content"],
      query: "this that thus",
      minimum_should_match: 2,
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "fields": [
        "title",
        "content"
      ],
      "query": "this that thus",
      "minimum_should_match": 2
    }
  }
}

Приведённый выше пример создаёт булевый запрос:

((content:this content:that content:thus) | (title:this title:that title:thus))

который соответствует документам с дизъюнкцией max по полям title и content. Здесь параметр minimum_should_match нельзя применять.

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "title",
                "content"
            ],
            "query": "this OR that OR thus",
            "minimum_should_match": 2
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'title',
          'content'
        ],
        query: 'this OR that OR thus',
        minimum_should_match: 2
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "title",
	        "content"
	      ],
	      "query": "this OR that OR thus",
	      "minimum_should_match": 2
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["title", "content"],
      query: "this OR that OR thus",
      minimum_should_match: 2,
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "fields": [
        "title",
        "content"
      ],
      "query": "this OR that OR thus",
      "minimum_should_match": 2
    }
  }
}

Добавление явных операторов заставляет рассматривать каждый термин как отдельное положение.

Приведённый выше пример создаёт булевый запрос:

((content:this | title:this) (content:that | title:that) (content:thus | title:thus))~2

который соответствует документам как минимум с двумя из трёх положений «должно», каждое из которых состоит из дизъюнкции max по полям для каждого термина.

Как minimum_should_match работает для поиска по пересекающимся полям

Значение cross_fields в поле type указывает поля с одинаковым анализатором, которые группируются вместе при анализе ввода.

resp = client.search(
    query={
        "query_string": {
            "fields": [
                "title",
                "content"
            ],
            "query": "this OR that OR thus",
            "type": "cross_fields",
            "minimum_should_match": 2
        }
    },
)
print(resp)
response = client.search(
  body: {
    query: {
      query_string: {
        fields: [
          'title',
          'content'
        ],
        query: 'this OR that OR thus',
        type: 'cross_fields',
        minimum_should_match: 2
      }
    }
  }
)
puts response
res, err := es.Search(
	es.Search.WithBody(strings.NewReader(`{
	  "query": {
	    "query_string": {
	      "fields": [
	        "title",
	        "content"
	      ],
	      "query": "this OR that OR thus",
	      "type": "cross_fields",
	      "minimum_should_match": 2
	    }
	  }
	}`)),
	es.Search.WithPretty(),
)
fmt.Println(res, err)
const response = await client.search({
  query: {
    query_string: {
      fields: ["title", "content"],
      query: "this OR that OR thus",
      type: "cross_fields",
      minimum_should_match: 2,
    },
  },
});
console.log(response);
GET /_search
{
  "query": {
    "query_string": {
      "fields": [
        "title",
        "content"
      ],
      "query": "this OR that OR thus",
      "type": "cross_fields",
      "minimum_should_match": 2
    }
  }
}

Приведённый выше пример создаёт булевый запрос:

(blended(terms:[field2:this, field1:this]) blended(terms:[field2:that, field1:that]) blended(terms:[field2:thus, field1:thus]))~2

который соответствует документам как минимум с двумя из трёх объединённых запросов по каждому термину.

Разрешение ресурсоёмких запросов

Запрос строки запроса может быть интерпретирован как prefix query, что означает, что если запросы префиксов отключены, как описано здесь, запрос не будет выполнен, и будет выброшено исключение.

© 2023-2025 Elasticsearch
As of September 2024, Elasticsearch is available under a choice of three licenses: the Server Side Public License (SSPL), the Elastic License, or the AGPLv3 (OSI approved).
Elasticsearch and the Elasticsearch logo are trademarks of Elasticsearch B.V., registered in the U.S. and in other countries.
https://www.elastic.co/guide/en/elasticsearch/reference/8.17/query-dsl-query-string-query.html

END_OF_DOCUMENT_MARKER

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API