Поиск в Hibernate: обновление индексного документа путем удаления дочерней сущности делает дочернюю сущность сиротой в индексном документе - PullRequest
0 голосов
/ 20 февраля 2020

Вот так настроена моя сущность

@Entity
@Indexed
public class Book{

    @OneToOne(cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.EAGER, mappedBy = "book")
    @IndexedEmbedded
    private FrontPage frontPage;

...//other data
}
@Entity
public class FrontPage{

    @OneToOne(cascade = {}, fetch = FetchType.EAGER, targetEntity = Book.class)
    @JoinColumn(name = "book_id", nullable = false)
    @ContainedIn
    private Book book;

...//other data

}

Так выглядит мой интеграционный тест

@Test
public void testMerge_RemoveFrontPage() {
    insertDataSet("dataset.xml");

    Book book = getEntityManager().find(Book.class, 2000L);
    //this book instance already have data

    book.setFrontPage(null);

    dao.merge(book);

    //verify after commit
    //In database the FrontPage entity reference is removed

}

При просмотре базы данных сущность FrontPage удаляется, но в Индексе книги все еще я вижу данные FrontPage.

то же самое происходит, если я попытался заменить данные FrontPage, как это, и в индексе Книги теперь я вижу две данные FrontPage.

book.setFrontPage(new FrontPage);

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

org.hibernate.search.event.impl. FullTextIndexEventListener: 250 - HSEARCH000024: невозможно переиндексировать сущность при изменении коллекции, невозможно извлечь идентификатор: com.xxxFrontPage

Не уверен, что здесь происходит неправильно или это ожидаемое поведение?

Hibernate Я использую следующие версии:

hibernate-search -asticsearch, hibernate-search-orm = 5.11.4.Final

1 Ответ

0 голосов
/ 20 февраля 2020

По умолчанию индексирование выполняется в серверной части Elasticsearch практически в режиме реального времени, что означает, что для отображения изменений в поисковых запросах требуется некоторое время. По умолчанию это занимает всего одну секунду.

Вы можете запросить refre sh после каждого проиндексированного документа, установив для свойства hibernate.search.default.elasticsearch.refresh_after_write значение true. Если вы сделаете это, эти изменения будут видны сразу после принятия транзакции. Однако это приведет к снижению производительности, поэтому я бы не рекомендовал ее использовать на производстве: просто используйте ее для испытаний.

Из документации :

Выполнять ли явное refre sh после выполнения набора операций с указанным c индексом (true или false)

hibernate.search.default.elasticsearch.refresh_after_write false (default)

Это полезно в модульных тестах, чтобы гарантировать, что запись выполнена видно по запросу сразу же без задержки. Это упрощает юнит-тесты. Вы не должны полагаться на синхронное поведение для своего производственного кода, за исключением редких случаев, поскольку Elasticsearch оптимизирован для асинхронной записи: оставьте значение false для оптимальной производительности.

...