spring-data-mongodb icon indicating copy to clipboard operation
spring-data-mongodb copied to clipboard

Java 17 InaccessibleObjectException when using java.time.Instant

Open saragluna opened this issue 3 years ago • 3 comments
trafficstars

I used the Instant in my model and got this error:

Caused by: java.lang.reflect.InaccessibleObjectException: Unable to make private java.time.Instant(long,int) accessible: module java.base does not "opens java.time" to unnamed module @32cf48b7
	at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:354)
	at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:297)
	at java.base/java.lang.reflect.Constructor.checkCanSetAccessible(Constructor.java:188)
	at java.base/java.lang.reflect.Constructor.setAccessible(Constructor.java:181)
	at org.springframework.util.ReflectionUtils.makeAccessible(ReflectionUtils.java:201)
	at org.springframework.data.mapping.PreferredConstructor.<init>(PreferredConstructor.java:53)
	at org.springframework.data.mapping.model.PreferredConstructorDiscoverer$Discoverers.buildPreferredConstructor(PreferredConstructorDiscoverer.java:250)
	at org.springframework.data.mapping.model.PreferredConstructorDiscoverer$Discoverers$1.discover(PreferredConstructorDiscoverer.java:137)
	at org.springframework.data.mapping.model.PreferredConstructorDiscoverer.discover(PreferredConstructorDiscoverer.java:82)
	at org.springframework.data.mapping.model.InstanceCreatorMetadataDiscoverer.discover(InstanceCreatorMetadataDiscoverer.java:81)
	at org.springframework.data.mapping.model.BasicPersistentEntity.<init>(BasicPersistentEntity.java:113)
	at org.springframework.data.mongodb.core.mapping.BasicMongoPersistentEntity.<init>(BasicMongoPersistentEntity.java:84)
	at org.springframework.data.mongodb.core.mapping.MongoMappingContext.createPersistentEntity(MongoMappingContext.java:88)
	at org.springframework.data.mongodb.core.mapping.MongoMappingContext.createPersistentEntity(MongoMappingContext.java:41)
	at org.springframework.data.mapping.context.AbstractMappingContext.doAddPersistentEntity(AbstractMappingContext.java:403)
	at org.springframework.data.mapping.context.AbstractMappingContext.addPersistentEntity(AbstractMappingContext.java:379)
	at org.springframework.data.mapping.context.AbstractMappingContext$PersistentPropertyCreator.lambda$createAndRegisterProperty$3(AbstractMappingContext.java:591)
	at java.base/java.lang.Iterable.forEach(Iterable.java:75)
	at org.springframework.data.mapping.context.AbstractMappingContext$PersistentPropertyCreator.createAndRegisterProperty(AbstractMappingContext.java:588)
	at org.springframework.data.mapping.context.AbstractMappingContext$PersistentPropertyCreator.doWith(AbstractMappingContext.java:542)
	at org.springframework.util.ReflectionUtils.doWithFields(ReflectionUtils.java:711)
	at org.springframework.data.mapping.context.AbstractMappingContext.doAddPersistentEntity(AbstractMappingContext.java:422)
	at org.springframework.data.mapping.context.AbstractMappingContext.addPersistentEntity(AbstractMappingContext.java:379)
	at org.springframework.data.mapping.context.AbstractMappingContext.getPersistentEntity(AbstractMappingContext.java:280)
	at org.springframework.data.mapping.context.AbstractMappingContext.getPersistentEntity(AbstractMappingContext.java:206)
	at org.springframework.data.mapping.context.AbstractMappingContext.getPersistentEntity(AbstractMappingContext.java:92)
	at org.springframework.data.mapping.context.MappingContext.getRequiredPersistentEntity(MappingContext.java:74)
	at org.springframework.data.mongodb.repository.support.MongoRepositoryFactory.getEntityInformation(MongoRepositoryFactory.java:146)
	at org.springframework.data.mongodb.repository.support.MongoRepositoryFactory.getEntityInformation(MongoRepositoryFactory.java:140)
	at org.springframework.data.mongodb.repository.support.MongoRepositoryFactory.getRepositoryFragments(MongoRepositoryFactory.java:119)
	at org.springframework.data.mongodb.repository.support.MongoRepositoryFactory.getRepositoryFragments(MongoRepositoryFactory.java:92)
	at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepositoryComposition(RepositoryFactorySupport.java:428)
	at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:293)
	at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.lambda$afterPropertiesSet$5(RepositoryFactoryBeanSupport.java:279)
	at org.springframework.data.util.Lazy.getNullable(Lazy.java:229)
	at org.springframework.data.util.Lazy.get(Lazy.java:113)
	at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.afterPropertiesSet(RepositoryFactoryBeanSupport.java:285)
	at org.springframework.data.mongodb.repository.support.MongoRepositoryFactoryBean.afterPropertiesSet(MongoRepositoryFactoryBean.java:101)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1799)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1749)
	... 79 more

I'm using the spring-data-mongodb version 4.0.0-M6.

saragluna avatar Oct 12 '22 14:10 saragluna

This is caused by JEP 396, Java 17 has more restrictive approach regarding modules. As a workaround you have to pass --add-opens=java.base/java.time=ALL-UNNAMED with specified module and package in JVM args but it may break again once Java 18 rolls out.

kkurczewski avatar Oct 13 '22 08:10 kkurczewski

To be more precise, it's due to the fact that SpringData use the Spring Commons converter mechanism as a principal way to read data from mongodb, and the converter use Constructor (and try to make private one accessible) as a main way to initialize the data. And doing so with java.time class throw this exception. One solution could be to interconnect more tightly Spring Data reading part and mongoDb connect.

PierrickPuimeanChieze avatar Oct 13 '22 08:10 PierrickPuimeanChieze

I'm confused by this two line of codes:

https://github.com/spring-projects/spring-data-mongodb/blob/240e53794c8868c204f4154ab0dbbd2070753cab/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/mapping/MongoSimpleTypes.java#L76

https://github.com/spring-projects/spring-data-mongodb/blob/240e53794c8868c204f4154ab0dbbd2070753cab/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/mapping/MongoSimpleTypes.java#L126-L128

Seems like Instant is considered as a simple type, but in that isSimpleType it excludes the java.time package.

But Spring Data Commons' behavior is different

https://github.com/spring-projects/spring-data-commons/blob/ac2f8ded22b3708c14d34958627e3c36a3df9e28/src/main/java/org/springframework/data/mapping/model/SimpleTypeHolder.java#L141-L175

saragluna avatar Oct 13 '22 08:10 saragluna

The error can occur when using a not fully intialized mapping context. Please help us analyze the issue and provide a complete minimal sample (something that we can unzip or git clone, build, and deploy) that reproduces the problem.

christophstrobl avatar Oct 28 '22 05:10 christophstrobl

If you would like us to look at this issue, please provide the requested information. If the information is not provided within the next 7 days this issue will be closed.

spring-projects-issues avatar Nov 04 '22 05:11 spring-projects-issues

Closing due to lack of requested feedback. If you would like us to look at this issue, please provide the requested information and we will re-open the issue.

spring-projects-issues avatar Nov 11 '22 05:11 spring-projects-issues