javaspringhazelcastehcache

Java 17 + Spring boot 3 migration - EhCache conflicting with Hazelcast


I'm migrating my app from Java 8 and Spring Boot 2.7.18 to Java 17 and Spring Boot 3.2.3.

I'm trying to migrate EhCache (i resorted to this link for migration, as my previous config fit the "old" definition), and i get the following error:

org.hibernate.service.spi.ServiceException: Unable to create requested service [org.hibernate.cache.spi.CacheImplementor] due to: Cache provider not started

javax.cache.CacheException: Multiple CachingProviders have been configured when only a single CachingProvider is expected

Now initially i thought i was configuring EhCache wrong, however i later found via this answer that my spring application is using hazelcast as a caching provider by default, which is causing a conflict between ehcache and hazelcast (multiple cache providers) when i enable EhCache.

enter image description here

It, however, does not do this in the previous stack of Java 8 and Spring Boot 2, so i'd like to know what i could do to disable this without having to resort to this answer as i do not want code in my spring main.

NOTE that i do have hazelcast in my project but it is enabled via application.yaml and should not be enabled on application startup.

Additionally, i have made no changes to my code whatsoever (other than changing javax to jakarta), i am simply updating versions of dependencies and changing the yaml properties of ehcache.

My pom contains the following dependencies:

<dependency>
    <groupId>com.hazelcast</groupId>
    <artifactId>hazelcast</artifactId>
    <version>${hazelcast.version}</version>
</dependency>
<dependency>
    <groupId>com.hazelcast</groupId>
    <artifactId>hazelcast-spring</artifactId>
    <version>${hazelcast.version}</version>
</dependency>
<dependency>
    <groupId>com.hazelcast</groupId>
    <artifactId>hazelcast-kubernetes</artifactId>
    <version>${hazelcast-kubernetes.version}</version>
</dependency>
<dependency>
    <groupId>org.hibernate.orm</groupId>
    <artifactId>hibernate-ehcache</artifactId>
    <version>${hibernate-ehcache.version}</version>
</dependency>
<dependency>
    <groupId>org.hibernate.orm</groupId>
    <artifactId>hibernate-jcache</artifactId>
    <version>${hibernate-jcache.version}</version>
</dependency>
<dependency>
    <groupId>org.ehcache</groupId>
    <artifactId>ehcache</artifactId>
    <version>${ehcache.version}</version>
</dependency>

with the following versions

<hazelcast-kubernetes.version>2.2.3</hazelcast-kubernetes.version>
<hazelcast.version>5.3.6</hazelcast.version>
<hibernate-ehcache.version>6.0.0.Alpha7</hibernate-ehcache.version>
<hibernate-jcache.version>6.4.4.Final</hibernate-jcache.version>
<ehcache.version>3.10.8</ehcache.version>

I used the answer that i previously mentioned, which had positive results, however i expect to not have to use code in my main to have ehcache working properly so i'd like spring not to consider hazelcast as my default caching provider.


Solution

  • When multiple JCache providers are present in your classpath, you can specify which one to use by including the following line in your application.properties:

    spring.jpa.properties.hibernate.javax.cache.provider=org.ehcache.jsr107.EhcacheCachingProvider
    

    If you don't specify this property, the hibernate-jcache will try to auto discover the providers. Then it finds two providers (ECache and HZ) and consequently, it leads to the occurrence of the exception.