Мультизапросы, или пакеты запросов, позволяют отправлять несколько поисковых запросов в Manticore в одном сетевом запросе.
👍 Почему стоит использовать мультизапросы?
Основная причина — производительность. Отправляя запросы в Manticore пакетами, а не по одному, вы экономите время за счёт уменьшения количества сетевых обращений. Кроме того, отправка запросов пакетами позволяет Manticore выполнять определённые внутренние оптимизации. Если оптимизации пакета применить нельзя, запросы будут обработаны по отдельности.
⛔ Когда не стоит использовать мультизапросы?
Мультизапросы требуют, чтобы все поисковые запросы в пакете были независимы, что бывает не всегда. Иногда запрос B зависит от результатов запроса A, то есть запрос B можно сформировать только после выполнения запроса A. Например, вы можете захотеть показать результаты из вторичного индекса только если в основной таблице не было найдено результатов, или указать смещение во втором наборе результатов на основе количества совпадений в первом наборе. В таких случаях нужно использовать отдельные запросы (или отдельные пакеты).
Вы можете выполнять несколько поисковых запросов в SQL, разделяя их точкой с запятой. Когда Manticore получает такой запрос от клиента, применяются все оптимизации между запросами.
Мультизапросы не поддерживают запросы с FACET. Количество мультизапросов в одном пакете не должно превышать max_batch_queries.
- SQL
SELECT id, price FROM products WHERE MATCH('remove hair') ORDER BY price DESC; SELECT id, price FROM products WHERE MATCH('remove hair') ORDER BY price ASCСуществует две основные оптимизации, о которых стоит знать: оптимизация общих запросов и оптимизация общих поддеревьев.
Оптимизация общих запросов означает, что searchd определит все запросы в пакете, которые отличаются только настройками сортировки и группировки, и выполнит поиск только один раз. Например, если пакет состоит из 3 запросов, все они по запросу "ipod nano", но первый запрос запрашивает топ-10 результатов, отсортированных по цене, второй группирует по ID поставщика и запрашивает топ-5 поставщиков, отсортированных по рейтингу, а третий запрашивает максимальную цену, полнотекстовый поиск по "ipod nano" будет выполнен только один раз, а его результаты будут использованы для построения трёх разных наборов результатов.
Фасетный поиск — особенно важный случай, который выигрывает от этой оптимизации. Действительно, фасетный поиск можно реализовать, выполняя несколько запросов: один для получения самих результатов поиска и несколько других с тем же полнотекстовым запросом, но с разными настройками группировки, чтобы получить все необходимые группы результатов (топ-3 авторов, топ-5 поставщиков и т.д.). Пока полнотекстовый запрос и настройки фильтрации остаются одинаковыми, сработает оптимизация общих запросов, значительно улучшая производительность.
Оптимизация общих поддеревьев ещё интереснее. Она позволяет searchd использовать сходства между пакетными полнотекстовыми запросами. Он выявляет общие части полнотекстовых запросов (поддеревья) во всех запросах и кэширует их между запросами. Например, рассмотрим следующий пакет запросов:
donald trump president
donald trump barack obama john mccain
donald trump speech
Есть общая двухсловная часть donald trump, которую можно вычислить один раз, затем закэшировать и использовать во всех запросах. Именно это и делает оптимизация общих поддеревьев. Размер кэша на запрос строго контролируется директивами subtree_docs_cache и subtree_hits_cache (чтобы кэширование всех шестнадцати миллиардов документов, соответствующих "i am", не исчерпало оперативную память и не убило сервер).
Как узнать, были ли запросы в пакете действительно оптимизированы? Если да, в соответствующем логе запросов появится поле "multiplier", указывающее, сколько запросов было обработано вместе:
Обратите внимание на поле "x3". Это означает, что запрос был оптимизирован и обработан в под-пакете из 3 запросов.
- log
[Sun Jul 12 15:18:17.000 2009] 0.040 sec x3 [ext/0/rel 747541 (0,20)] [lj] the
[Sun Jul 12 15:18:17.000 2009] 0.040 sec x3 [ext/0/ext 747541 (0,20)] [lj] the
[Sun Jul 12 15:18:17.000 2009] 0.040 sec x3 [ext/0/ext 747541 (0,20)] [lj] theДля сравнения, вот как выглядел бы обычный лог, если бы запросы не были объединены в пакет:
- log
[Sun Jul 12 15:18:17.062 2009] 0.059 sec [ext/0/rel 747541 (0,20)] [lj] the
[Sun Jul 12 15:18:17.156 2009] 0.091 sec [ext/0/ext 747541 (0,20)] [lj] the
[Sun Jul 12 15:18:17.250 2009] 0.092 sec [ext/0/ext 747541 (0,20)] [lj] theОбратите внимание, что время на запрос в случае мультизапроса улучшилось в 1.5–2.3 раза, в зависимости от конкретного режима сортировки.