We would like to handle the indexing ourselves for one of our Hibernate Search entities.
Is it possible to disable auto indexing within Hibernate Search 6 for a specific entity? Similar to the older Hibernate Search global setting: hibernate.search.indexing_strategy = manual
I've searched through the documentation but haven't seen this mentioned.
CodePudding user response:
hibernate.search.indexing_strategy = manual
was for all entity types, not for a specific one.
The feature you're looking for has already been filed as HSEARCH-168, and is currently planned for Hibernate Search 6.2.
In the meantime, I think the best you can do would be to rely on a hack. It won't be as efficient as what we envision for HSEARCH-168, but it's a start:
- Implement a RoutingBridge which, based on a switch, will either disable indexing completely (both adding and removing the entity from the index) or behave normally as if there was no routing bridge:
public class ManualIndexingRoutingBinder implements RoutingBinder { private static volatile boolean indexingEnabled = false; public static synchronized void withIndexingEnabled(Runnable runnable) { indexingEnabled = true; try { runnable.run(); } finally { indexingEnabled = false; } } @Override public void bind(RoutingBindingContext context) { context.dependencies() .useRootOnly(); context.bridge( Book.class, new Bridge() ); } public static class Bridge implements RoutingBridge<Book> { @Override public void route(DocumentRoutes routes, Object entityIdentifier, Book indexedEntity, RoutingBridgeRouteContext context) { if ( indexingEnabled ) { routes.addRoute(); } else { routes.notIndexed(); } } @Override public void previousRoutes(DocumentRoutes routes, Object entityIdentifier, Book indexedEntity, RoutingBridgeRouteContext context) { if ( indexingEnabled ) { // So that Hibernate Search will correctly delete entities if necessary. // Only useful if you use SearchIndexingPlan for manual indexing, // as the MassIndexer never deletes documents. routes.addRoute(); } else { routes.notIndexed(); } } } }
- Apply that routing bridge to the entity types you want to control:
@Entity @Indexed(routingBinder = @RoutingBinderRef(type = ManualIndexingRoutingBinder.class)) public class Book { // ... }
- The routing bridge will effectively disable automatic indexing.
- To index manually, do this:
ManualIndexingRoutingBinder.withIndexingEnabled(() -> { Search.mapping(entityManagerFactory).scope(Book.class) .massIndexer() .startAndWait(); });
I didn't test this exactly, so please report back, but in principle this should work.