В предыдущем сообщении в блоге об автозаполнении в многозначном поле мы обсуждали, как выделение может помочь нам получить интересующую нас информацию . Мы также пообещали, что вернемся к этой теме и покажем, как добиться аналогичной функциональности с помощью использование Solr возможностей огранки. Итак, давайте сделаем это.
Прежде чем мы начнем
Поскольку этот пост является более или менее продолжением того, что мы писали ранее об автозаполнении многозначных полей, мы рекомендуем прочитать « Автозаполнение многозначных полей с помощью выделения » перед прочтением оставшейся части этой записи. Мы также хотели бы отметить, что метод, показанный в этой записи, очень похож на метод, показанный в посте « Solr и автозаполнение (часть 1) », но мы хотели обновить эту тему и показать пример с использованием многозначных полей ,
конфигурация
Как и в предыдущем посте, мы начнем с настройки Solr.
Структура индекса
Структура нашего индекса точно такая же, как и ранее показанная, но давайте вспомним это. Одно — пожалуйста, помните, что мы хотим, чтобы автозаполнение работало над многозначным полем. Это поле называется функциями, и вся конфигурация полей индекса выглядит следующим образом:
<fields> <field name="id" type="string" indexed="true" stored="true" required="true" multiValued="false" /> <field name="features" type="string" indexed="true" stored="true" multiValued="true"/> <field name="features_autocomplete" type="text_autocomplete" indexed="true" stored="true" multiValued="true"/> <field name="_version_" type="long" indexed="true" stored="true"/> </fields>
Для получения значений для автозаполнения мы будем использовать поле features_autocomplete .
Копировать поле
Конечно, мы не хотим менять наш индексатор, и мы хотим, чтобы Solr автоматически копировал данные из поля функций в поле features_autocomplete . Из — за этого мы добавим copyField определение в schema.xml файл, так что это выглядит следующим образом :
<copyField source="features" dest="features_autocomplete"/>
Наш тип поля text_autocomplete
И мы пришли к первому отличию — типу поля text_autocomplete . На этот раз это выглядит так:
<fieldType name="text_autocomplete" class="solr.TextField" positionIncrementGap="100"> <analyzer> <tokenizer class="solr.KeywordTokenizerFactory"/> <filter class="solr.LowerCaseFilterFactory"/> </analyzer> </fieldType>
В связи с тем, что мы будем использовать фасетирование, мы используем solr.KeywordTokenizerFactory с solr.LowerCaseFilterFactory, чтобы данные в нашем поле были единым токеном в нижнем регистре.
Пример данных
Данные нашего примера идентичны тем, что были у нас ранее, но давайте вспомним их для ясности:
<add> <doc> <field name="id">1</field> <field name="features">Multiple windows</field> <field name="features">Single door</field> </doc> <doc> <field name="id">2</field> <field name="features">Single window</field> <field name="features">Single door</field> </doc> <doc> <field name="id">3</field> <field name="features">Multiple windows</field> <field name="features">Multiple doors</field> </doc> </add>
Запрос с огранкой
Давайте посмотрим, как будет выглядеть наш запрос, когда мы будем использовать фасетку вместо выделения.
Полный запрос
При использовании огранки наш запрос должен выглядеть примерно так:
q=*:*&rows=0&facet=true&facet.field=features_autocomplete&facet.prefix=sing
Несколько слов о параметрах:
- rows = 0 — мы говорим Solr, что нам не нужны документы, соответствующие запросу в результатах,
- facet = true — мы сообщаем Solr, что хотим использовать фасетку,
- facet.field = features_autocomplete — мы говорим, какое поле будет использоваться для расчета фасетирования,
- facet.prefix = sing — с помощью этого параметра мы предоставляем значение запроса для автозаполнения.
Результаты запроса
Результаты запроса, возвращаемые Solr для указанного выше запроса:
<?xml version="1.0" encoding="UTF-8"?> <response> <lst name="responseHeader"> <int name="status">0</int> <int name="QTime">0</int> <lst name="params"> <str name="facet">true</str> <str name="q">*:*</str> <str name="facet.prefix">sing</str> <str name="facet.field">features_autocomplete</str> <str name="rows">0</str> </lst> </lst> <result name="response" numFound="3" start="0"> </result> <lst name="facet_counts"> <lst name="facet_queries"/> <lst name="facet_fields"> <lst name="features_autocomplete"> <int name="single door">2</int> <int name="single window">1</int> </lst> </lst> <lst name="facet_dates"/> <lst name="facet_ranges"/> </lst> </response>
Как вы можете видеть в разделе огранки полей, мы получили интересующие нас фразы и количество документов, в которых они появляются.
О чем помнить
Важно помнить, что значение, предоставленное параметру facet.prefix, не анализируется. Из-за этого, если бы мы предоставили значение Sing вместо sing, мы не получили бы результаты. Вы должны помнить это.
Краткое резюме
В приведенной выше записи показан второй метод, используемый для разработки функции автозаполнения многозначных полей. Конечно, мы не сказали все о теме, и мы вернемся к ней когда-нибудь, но пока это все. Мы надеемся, что кто-то найдет это полезным