Как исключить некоторые объекты из индекса с помощью Hibernate Search? - PullRequest
0 голосов
/ 27 сентября 2011

Мы хотим включить полнотекстовый поиск в базе данных Hibernate только для некоторых объектов определенной сущности.Есть ли способ запретить поиску в спящем режиме индексировать некоторые экземпляры этого объекта?Мы не хотим фильтровать результаты поиска, мы просто хотим, чтобы некоторые экземпляры вообще не индексировались.

Пример: у нас есть база данных с работниками, как активными, так и вышедшими на пенсию.Нам не нужно искать пенсионеров.Мы очень старая IT-компания, основанная в 1695 году, поэтому у нас около 2 миллионов пенсионеров, которых мы очень любим, но не хотим индексировать, только 10 активных.Есть ли способ, с помощью которого Hibernate Search можно указывать только тех сотрудников, которые ушли на пенсию = false?

С уважением, Йохен

Ответы [ 2 ]

0 голосов
/ 28 сентября 2011

Не думаю, что вы должны работать с IndexReader непосредственно в прослушивателе событий. Вместо этого вам следует расширить (или написать новую версию) существующий FullTextIndexEventListener и проверить вашу сущность в методе обратного вызова и в зависимости от вызова удаленного поля или без вызова processWork .

Если вы хотите использовать Hibernate Search 4 (вместе с Hibernate Core 4), вам также потребуется пользовательский HibernateSearchIntegrator .

Это решение будет работать, но его следует рассматривать как временное решение до тех пор, пока не будет реализовано HSEARCH-471 .

0 голосов
/ 27 сентября 2011

Вам понадобится PreUpdateEventListener, в этом слушателе проверьте сущность и определите, хотите ли вы добавить ее в индекс lucene.

Этот код не гарантированно работает, но, надеюсь, вы поймете идею.

public class LuceneUpdateListener implements PreUpdateEventListener {

    protected FSDirectory directory; // = path to lucene index

    public boolean onPreUpdate(PreUpdateEvent event)  {
        if (event.getEntity() instanceof Employee ) {

                try {       

                    Employee employee = (Employee) event.getEntity();

                    //Remove on update
                    remove((Employee) event.getEntity(), (Long) event.getId(), directory);

                    //Add it back if this instance should be indexed
                    try { 
                        if (employee.shouldBeIndexed()) {
                            add((Employee) event.getEntity(), (Long) event.getId(), directory);                         
                        }
                    } 
                    catch (Exception e) {

                    }
                } 
                catch (Exception e) {
                    throw new CallbackException(e.getMessage());
                }
            }
        }
        return false;
    }


    protected synchronized void add(Employee employee, Id employeeId, FSDirectory directory) {
          try{
            IndexWriter writer = new IndexWriter(directory, new StandardAnalyzer(), false);
            Document d = LuceneDocumentFactory.makeDocument(employee);
            writer.addDocument(d);
            writer.close();
            directory.close();
            }
            catch(Exception e) { 

            }
    }

    protected synchronized void remove(Long id, FSDirectory directory) throws IOException {
            try {
                IndexReader ir = IndexReader.open(directory); 
                ir.deleteDocuments(new Term("id", id.toString()));
                ir.close();
            }        
            catch(Exception e) {                
            }   
    }

    public FSDirectory getDirectory() {
            return directory;
    }

    public void setDirectory(FSDirectory directory) {
        this.directory = directory;
    }

}

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

Также не забудьте зарегистрировать слушателя.

...