Zend Lucene исчерпывает память при индексации - PullRequest
3 голосов
/ 11 сентября 2011

Старый сайт, который я поддерживаю, использует Zend Lucene (ZF 1.7.2) в качестве поисковой системы. Недавно я добавил две новые таблицы для индексации, которые содержат около 2000 строк текстовых данных размером от 31 байта до 63 КБ.

Индексация работала нормально несколько раз, но после третьего запуска или около того она начала заканчиваться фатальной ошибкой из-за исчерпания выделенной памяти. Ограничение памяти PHP изначально было установлено в 16M, что было достаточно для индексации всего другого контента, 200 строк текста по несколько килобайт каждый. Я постепенно увеличил лимит памяти до 160 МБ, но его все равно недостаточно, и я не могу увеличить его еще больше.

При индексировании мне сначала нужно очистить ранее проиндексированные результаты, потому что схема пути содержит числа, которые Lucene, похоже, воспринимает как стоп-слова, возвращая каждую запись, когда я запускаю этот поиск:

$this->index->find('url:/tablename/12345');

После очистки всех результатов я вставляю их один за другим:

foreach($urls as $v) {
   $doc = new Zend_Search_Lucene_Document();
   $doc->addField(Zend_Search_Lucene_Field::UnStored('content', $v['data']);
   $doc->addField(Zend_Search_Lucene_Field::Text('title', $v['title']);
   $doc->addField(Zend_Search_Lucene_Field::Text('description', $v['description']);
   $doc->addField(Zend_Search_Lucene_Field::Text('url', $v['path']);
   $this->index->addDocument($doc);
}

После примерно тысячи итераций индексатору не хватает памяти и происходит сбой. Странно, удвоение лимита памяти помогает только нескольким десяткам строк.

Я уже пытался настроить параметры MergeFactor и MaxMergeDocs (до значений 5 и 100 соответственно) и вызывать $this->index->optimize() каждые 100 строк, но ни одна из них не обеспечивает последовательной помощи.

Очистка всего поискового индекса и его перестройка в большинстве случаев приводит к успешной индексации, но я бы предпочел более элегантное и менее ресурсоемкое решение. Я что-то не так делаю? Это нормально, если индексирование занимает так много памяти?

1 Ответ

1 голос
/ 07 августа 2012

У меня была похожая проблема для сайта, который я должен был поддерживать, который имел как минимум три разных языка и должен был переиндексировать те же 10 000 + (и растущие) локализованные документы для каждой отдельной локали отдельно (каждый из которых использовал свой собственный язык).локализованная поисковая система).Достаточно сказать, что обычно это не удалось в течение второго прохода.

В итоге мы реализовали процесс переиндексации на основе Ajax, который впервые вызвал скрипт для инициализации и начала переиндексации.Этот сценарий прервался с предварительно определенным числом обработанных документов и возвратил значение JSON, указывающее, было ли оно выполнено, вместе с другой информацией о ходе выполнения.Затем мы повторно вызывали тот же сценарий с переменными прогресса, пока сценарий не вернул завершенное состояние.

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

ДляВ работе cron мы просто создали скрипт bash, выполняющий ту же задачу, но с кодами выхода.

Это было около 3 лет назад, и с тех пор ничего не вышло.

...