В последнее время мне было очень весело взламывать кодек Lucene. Я надеюсь создать слой хранения Lucene на основе FoundationDB — нового распределенного и транзакционного хранилища ключей-значений. Это интересная возможность узнать как о FoundationDB, так и о низкоуровневых деталях Lucene.
Но прежде чем мы приступим ко всем этим забавным техническим вещам, нам нужно кое-что сделать. Наша цель — заставить MyFirstCodec работать! Вот исходный код:
public class MyCodec extends FilterCodec { public MyCodec() { super("MyCodec", new Lucene42Codec()); } }
Большой! Готово. Ну, не совсем. Настоящий кодек выглядит примерно так
public final class SimpleTextCodec extends Codec { // pretend there’s private vars here @Override public PostingsFormat postingsFormat() { return postings; } @Override public StoredFieldsFormat storedFieldsFormat() { return storedFields; } @Override public TermVectorsFormat termVectorsFormat() { return vectorsFormat; } @Override public FieldInfosFormat fieldInfosFormat() { return fieldInfosFormat; } @Override public SegmentInfoFormat segmentInfoFormat() { return segmentInfos; } @Override public NormsFormat normsFormat() { return normsFormat; } @Override public LiveDocsFormat liveDocsFormat() { return liveDocs; } @Override public DocValuesFormat docValuesFormat() { return dvFormat; } }
Этот пример немного более явный. Это кодек Mike McCandless SimpleText, который является отличным кодеком для просмотра в образовательных целях. В этом кодеке каждая часть класса настраивается.
Обычно вы хотите реализовать только подмножество компонентов кодека. Lucene предоставляет удобный базовый класс, который называется « FilterCodec ». Вы можете настроить любые части, которые вы хотите, делегируя остальное другому кодеку. Например, если мы должны были реализовать пользовательскую реализацию хранилища только для векторов терминов, мы можем переопределить так:
public class MyCodec extends FilterCodec { final private TermVectorsFormat myTermVectorsFormat; public MyCodec() { super("MyCodec", new Lucene42Codec()); myTermVectorsFormat = new MyTermVectorsFormat(); } // Use custom TermVectorsFormat, default everything else to Lucene42Codec public TermVectorsFormat termVectorsFormat() { return myTermVectorsFormat; } }
Здесь мы делегируем Lucene42Codec для всего, кроме нашего специального TermVectorsFormat.
Каждый из этих отдельных форматов — это отдельные части, отвечающие за сериализацию в резервное хранилище во время индексации и десериализации в память при обратном чтении в память. Для многих форматов это немного больше. Например, для формата проводок, формата, ответственного за хранение инвертированного индекса , жизненно важно иметь возможность эффективно перебирать инвертированный индекс. Хранение инвертированного индекса должно быть сделано таким образом, чтобы мы могли легко перебрать все проиндексированные поля, затем все термины, проиндексированные в этом поле, а затем, в свою очередь, документы с частотами терминов и позициями, которые содержат этот термин в этом поле.
Вы найдете аналогичные ограничения при реализации интерфейсов других частей кодека. Каждая из этих частей — отдельная тема, о которой стоит написать. Все они заслуживают своих собственных статей в блоге. На данный момент я призываю вас изучить JavaDocs, чтобы увидеть, что может быть интересно настроить на бэкенде Lucene! Прежде чем я оставлю вас в Javadocs, важно разобраться в нескольких деталях: построение и запуск тестов Lucene для вашего кодека.
Санитарно-технические работы! Модульные тесты и многое другое
Давайте позаботимся о небольшом количестве сантехники. Как нам настроить проект для кодека? Как мы запускаем тесты Lucene для нашей реализации, чтобы подтвердить, что Solr / Lucene будут работать с нашими изменениями?
Использование maven для настройки проекта довольно просто. К счастью, я создал приветственный проект Lucene Codec на github. Это захватывает настройку проекта с Maven. Не стесняйтесь раскошелиться, чтобы пропустить первые два шага ниже. Вам все еще нужно прочитать ниже, чтобы узнать, как запускать тесты Lucene для вашего кодека.
Во-первых , мы начнем с создания простого проекта maven с pom, который зависит от lucene-core в той версии, для которой вы ориентируетесь на свой кодек.
Во-вторых, нам нужно будет опубликовать через наш META-INF/services
каталог, что у нас есть класс, который реализует интерфейс Codec. Это рекламирует наш кодек для загрузчика классов Lucene. Под src/main/resources/services
создание файла называется org.apache.lucene.codecs.Codec
. В файле должна быть одна строка с полным именем вашего класса кодеков:
com.o19s.MyCodec
Нам нужно указать mvn скопировать это в целевой / META-INF, указав его в качестве ресурса, который будет скопирован в целевую папку:
<build> <resources> <resource> <directory>src/main/resources/services</directory> <targetPath>META-INF/services</targetPath> </resource> </resources> </build>
В-третьих, опустите полное дерево исходных текстов Lucene / Solr . Давайте проверим наш кодек из командной строки!
Упакуйте свой кодек в банку:
mvn package
Под деревом исходного кода Lucene выполните один тест Lucene. Передайте ему кодек для использования с аргументом -Dtests.codec. Передайте банку с кодеком, который вы только что упаковали с lib
аргументом. Выполнение этого докажет, что Lucene может найти и загрузить ваш кодек. Если Lucene не может найти загрузку вашего кодека, вы сразу же получите соответствующую ошибку.
C:\solr\solr-4.3.0\lucene>ant -Dtestcase=TestSegmentTermDocs - Dtests.codec=MyCodec –lib "C:\path\to\target\codec-1.0-SNAPSHOT.jar" test
Теперь запустите все тесты!
C:\solr\solr-4.3.0\lucene>ant -Dtests.codec=MyCodec –lib "C:\path\to\target\codec-1.0-SNAPSHOT.jar" test
В-четвертых , естественно будет удобно отлаживать модульные тесты Lucene, запускающие наш кодек в Eclipse. Вот что нам нужно сделать.
- Загрузите ваш кодек и исходный код Lucene в Eclipse .
- Создать новую конфигурацию отладки Junit
- Выберите переключатель для «Запустить все тесты в выбранном проекте, пакете или папке».
- Введите в папку / путь / к / lucene / core / src / test
- Выберите тестер JUNIT 4
-
На вкладке arguments для аргументов vm укажите:
-ea -Dtests.codec = MyCodec
-
На вкладке «classpath» убедитесь, что выбран ваш проект кодека и проект solr / lucene
Теперь вы сможете запустить эту конфигурацию отладки и отправиться в город! Выйди и сделай несколько классных кодеков! Дайте нам знать о кодеке, над которым вы работаете, очень рады услышать об этом!