Search code examples
javaelasticsearchjunithibernate-search

Unit testing hibernate search with elastic backend


We are using hibernate search and its orm mapper together with JPA for our Java based search services. The challenge I'm facing is to write unit tests, such as:

  • Insert JPA entity car "tesla v3"
  • Search for "tesla"
  • Validate the JPA entity "tesla v3" to be contained in the result set of hibernate search

To do so, my first thought was to run some kind of in-memory, single node elastic cluster, test against this cluster, and tear it down afterwards. But it seems that there exists no such thing.

The official documentation (https://docs.jboss.org/hibernate/stable/search/reference/en-US/html_single/) does not explain unit testing for hibernate search.

Now I'm curious how you test your hibernate search implementations. Do I need a test instance? Do you rename your indices for testing and clear it before each test run?

I'm grateful for every input!


Solution

  • I wouldn't call these "unit" tests since you're also testing an integration to another piece of software (Elasticsearch). What you're doing is, IMO, clearly integration tests.

    The easiest way to spin up Elasticsearch in your tests is probably to use TestContainers:

    If you use Quarkus, it's even easier as Quarkus will spin up an Elasticsearch instance automatically for your tests, thanks to Dev Services.

    As to initializing/resetting your indexes, it depends how you run your tests.

    If you start up a whole application for each test, you can just take advantage of automatic schema management to have Hibernate Search reset the indexes on startup/tear-down: just set hibernate.search.schema_management.strategy to drop-and-create-and-drop in your test configuration.

    If you start your application only once for your whole test class (that's typically the case for Spring tests) or test suite, then you can add methods annotated with JUnit's @Before/@After to manually re-create the indexes before or after each test, using Hibernate Search schema management API. JUnit provides various ways of writing that kind of code once and reusing it in all your tests: "rules" in JUnit 4, "extensions" in JUnit 5, ... But that will require more JUnit expertise.