Spring Data Redis on Spring Boot 2.1.0 and Java 11 not working - spring

I updated my application to Spring Boot 2.1.0 and Java 11. Since then my Redis is not working anymore.
When I call findById() and the result is empty then there are no problems.
When I call findById() and there is a result then the application / thread is stuck at this point and nothing happens.
When I use Spring Boot 2.0.6 and Java 9 the same code is working well.
I tried to use LettuceConnectionFactory and JedisConnectionFactory with the same result.
My Redis Config:
#Configuration
#EnableRedisRepositories
public class RedisConfiguration {
#Bean
RedisConnectionFactory connectionFactory() {
return new LettuceConnectionFactory();
}
#Bean
#Primary
RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory connectionFactory) {
RedisTemplate<String, Object> template = new RedisTemplate<>();
template.setConnectionFactory(connectionFactory);
template.setKeySerializer(new StringRedisSerializer());
template.setValueSerializer(new GenericJackson2JsonRedisSerializer());
return template;
}
}
My entity:
#Value
#RedisHash("token")
public class Token {
#Id
private String key;
private String value;
#TimeToLive
private Long expiration;
}
My repository just extends the CrudRepository and I'm only using provided methods.
Redis-Server version is Redis server v=4.0.9 running on OSX (dev) / Ubuntu (test).
Did I miss some changes I have to apply to use Java 11 / Boot 2.1 ?

Change the name of variable key to id.
There is a bug that makes the field with the #Id annotation have to be named id.
public class Token implements Serializable {
#Id private String id;
private String code;
#TimeToLive private Long expiration;
}

I found a solution. I created a test project and saw that the following exception was thrown by the CrudRepository#findById() method.
Caused by: org.springframework.data.keyvalue.core.UncategorizedKeyValueException: No accessor to set property #org.springframework.data.redis.core.TimeToLive(unit=SECONDS)private final java.lang.Long com.test.redisbug.Token.expiration!; nested exception is java.lang.UnsupportedOperationException: No accessor to set property #org.springframework.data.redis.core.TimeToLive(unit=SECONDS)private final java.lang.Long com.test.redisbug.Token.expiration!
at org.springframework.data.keyvalue.core.KeyValuePersistenceExceptionTranslator.translateExceptionIfPossible(KeyValuePersistenceExceptionTranslator.java:55) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.resolveExceptionIfPossible(KeyValueTemplate.java:462) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.execute(KeyValueTemplate.java:348) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.findById(KeyValueTemplate.java:251) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.repository.support.SimpleKeyValueRepository.findById(SimpleKeyValueRepository.java:129) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.data.repository.core.support.RepositoryComposition$RepositoryFragments.invoke(RepositoryComposition.java:359) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.repository.core.support.RepositoryComposition.invoke(RepositoryComposition.java:200) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$ImplementationMethodExecutionInterceptor.invoke(RepositoryFactorySupport.java:644) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.doInvoke(RepositoryFactorySupport.java:608) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.lambda$invoke$3(RepositoryFactorySupport.java:595) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.invoke(RepositoryFactorySupport.java:595) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.data.projection.DefaultMethodInvokingMethodInterceptor.invoke(DefaultMethodInvokingMethodInterceptor.java:59) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:93) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.data.repository.core.support.SurroundingTransactionDetectorMethodInterceptor.invoke(SurroundingTransactionDetectorMethodInterceptor.java:61) ~[spring-data-commons-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.1.2.RELEASE.jar:5.1.2.RELEASE]
at com.sun.proxy.$Proxy47.findById(Unknown Source) ~[na:na]
at com.test.redisbug.RedisBugApplication.run(RedisBugApplication.java:29) ~[classes/:na]
at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:813) ~[spring-boot-2.1.0.RELEASE.jar:2.1.0.RELEASE]
... 5 common frames omitted
Caused by: java.lang.UnsupportedOperationException: No accessor to set property #org.springframework.data.redis.core.TimeToLive(unit=SECONDS)private final java.lang.Long com.test.redisbug.Token.expiration!
at com.test.redisbug.Token_Accessor_wgdh2l.setProperty(Unknown Source) ~[classes/:na]
at org.springframework.data.redis.core.RedisKeyValueAdapter.readBackTimeToLiveIfSet(RedisKeyValueAdapter.java:622) ~[spring-data-redis-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.redis.core.RedisKeyValueAdapter.get(RedisKeyValueAdapter.java:300) ~[spring-data-redis-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.lambda$findById$3(KeyValueTemplate.java:253) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.execute(KeyValueTemplate.java:346) ~[spring-data-keyvalue-2.1.2.RELEASE.jar:2.1.2.RELEASE]
... 29 common frames omitted
I changed the #Value annoation on my entity to #Data #AllArgsConstructor and now it's working fine.
Seems like there were some changes in spring-data-redis.

I just had the same error and came to the solution by setting val to var in my kotlin model. I didn't use #value or #Data or #AllArgsConstructor.
#RedisHash("keys")
class Token (
#Id
val key: String? = null,
#TimeToLive
var expiration: Long
)
my logs looked like this:
org.springframework.data.keyvalue.core.UncategorizedKeyValueException: No accessor to set property #org.springframework.data.redis.core.TimeToLive(unit=SECONDS)private final long oauth2demo.oauth2clientdemo.Token.expiration!; nested exception is java.lang.UnsupportedOperationException: No accessor to set property #org.springframework.data.redis.core.TimeToLive(unit=SECONDS)private final long oauth2demo.oauth2clientdemo.Token.expiration!
at org.springframework.data.keyvalue.core.KeyValuePersistenceExceptionTranslator.translateExceptionIfPossible(KeyValuePersistenceExceptionTranslator.java:55) ~[spring-data-keyvalue-2.1.9.RELEASE.jar!/:2.1.9.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.resolveExceptionIfPossible(KeyValueTemplate.java:462) ~[spring-data-keyvalue-2.1.9.RELEASE.jar!/:2.1.9.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.execute(KeyValueTemplate.java:348) ~[spring-data-keyvalue-2.1.9.RELEASE.jar!/:2.1.9.RELEASE]
at org.springframework.data.keyvalue.core.KeyValueTemplate.findById(KeyValueTemplate.java:251) ~[spring-data-keyvalue-2.1.9.RELEASE.jar!/:2.1.9.RELEASE]
at org.springframework.data.keyvalue.repository.support.SimpleKeyValueRepos
...

Related

Why getting connection refused with elasticsearch 8 and springboot 3

I am trying to connect to elasticsearch 8 from my springboot 3 project floowing this official doc. But getting connection refused error without much details.
Here is my configuration
#Configuration
#Slf4j
#EnableElasticsearchRepositories(basePackages = "com....elastic")
public class ElasticConfig {
#Bean
public ClientConfiguration clientConfiguration() {
ClientConfiguration clientConfiguration = ClientConfiguration.builder()
.connectedTo("192.168.19.23:9200")
.usingSsl()
.withConnectTimeout(Duration.ofSeconds(5))
.withSocketTimeout(Duration.ofSeconds(3))
.withBasicAuth("elastic", "abc")
.build();
return clientConfiguration;
}
}
I have my SSL certificate in my jdk. The project runs properly but when it tries to save data on elasticsearch, it gets this error
org.springframework.dao.DataAccessResourceFailureException: Connection refused
at org.springframework.data.elasticsearch.client.elc.ElasticsearchExceptionTranslator.translateExceptionIfPossible(ElasticsearchExceptionTranslator.java:100)
at org.springframework.data.elasticsearch.client.elc.ElasticsearchExceptionTranslator.translateException(ElasticsearchExceptionTranslator.java:62)
at org.springframework.data.elasticsearch.client.elc.ElasticsearchTemplate.execute(ElasticsearchTemplate.java:540)
at org.springframework.data.elasticsearch.client.elc.ElasticsearchTemplate.doIndex(ElasticsearchTemplate.java:213)
at org.springframework.data.elasticsearch.core.AbstractElasticsearchTemplate.save(AbstractElasticsearchTemplate.java:204)
at org.springframework.data.elasticsearch.repository.support.SimpleElasticsearchRepository.lambda$save$5(SimpleElasticsearchRepository.java:172)
at org.springframework.data.elasticsearch.repository.support.SimpleElasticsearchRepository.executeAndRefresh(SimpleElasticsearchRepository.java:344)
at org.springframework.data.elasticsearch.repository.support.SimpleElasticsearchRepository.save(SimpleElasticsearchRepository.java:172)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at org.springframework.data.repository.core.support.RepositoryMethodInvoker$RepositoryFragmentMethodInvoker.lambda$new$0(RepositoryMethodInvoker.java:288)
at org.springframework.data.repository.core.support.RepositoryMethodInvoker.doInvoke(RepositoryMethodInvoker.java:136)
at org.springframework.data.repository.core.support.RepositoryMethodInvoker.invoke(RepositoryMethodInvoker.java:120)
at org.springframework.data.repository.core.support.RepositoryComposition$RepositoryFragments.invoke(RepositoryComposition.java:516)
at org.springframework.data.repository.core.support.RepositoryComposition.invoke(RepositoryComposition.java:285)
at org.springframework.data.repository.core.support.RepositoryFactorySupport$ImplementationMethodExecutionInterceptor.invoke(RepositoryFactorySupport.java:628)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.doInvoke(QueryExecutorMethodInterceptor.java:168)
at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.invoke(QueryExecutorMethodInterceptor.java:143)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:97)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:218)
at jdk.proxy2/jdk.proxy2.$Proxy131.save(Unknown Source)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:343)
at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:196)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:137)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:218)
at jdk.proxy2/jdk.proxy2.$Proxy131.save(Unknown Source)
at com...ServiceImpl.sendToElastic(ServiceImpl.java:171)
at com...ServiceImpl.getIdAndSend(ServiceImpl.java:132)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:568)
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:343)
at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:196)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:752)
at org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:123)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:388)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:119)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:752)
at org.springframework.aop.interceptor.AsyncExecutionInterceptor.lambda$invoke$0(AsyncExecutionInterceptor.java:115)
at org.springframework.util.concurrent.FutureUtils.lambda$toSupplier$0(FutureUtils.java:74)
at java.base/java.util.concurrent.CompletableFuture$AsyncSupply.run(CompletableFuture.java:1768)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1136)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:635)
at java.base/java.lang.Thread.run(Thread.java:833)
Caused by: java.lang.RuntimeException: Connection refused
at org.springframework.data.elasticsearch.client.elc.ElasticsearchExceptionTranslator.translateException(ElasticsearchExceptionTranslator.java:61)
... 56 common frames omitted
Caused by: java.net.ConnectException: Connection refused
at org.elasticsearch.client.RestClient.extractAndWrapCause(RestClient.java:930)
at org.elasticsearch.client.RestClient.performRequest(RestClient.java:300)
at org.elasticsearch.client.RestClient.performRequest(RestClient.java:288)
at co.elastic.clients.transport.rest_client.RestClientTransport.performRequest(RestClientTransport.java:147)
at co.elastic.clients.elasticsearch.ElasticsearchClient.index(ElasticsearchClient.java:962)
at org.springframework.data.elasticsearch.client.elc.ElasticsearchTemplate.lambda$doIndex$6(ElasticsearchTemplate.java:213)
at org.springframework.data.elasticsearch.client.elc.ElasticsearchTemplate.execute(ElasticsearchTemplate.java:538)
... 55 common frames omitted
Caused by: java.net.ConnectException: Connection refused
at java.base/sun.nio.ch.Net.pollConnect(Native Method)
at java.base/sun.nio.ch.Net.pollConnectNow(Net.java:672)
at java.base/sun.nio.ch.SocketChannelImpl.finishConnect(SocketChannelImpl.java:946)
at org.apache.http.impl.nio.reactor.DefaultConnectingIOReactor.processEvent(DefaultConnectingIOReactor.java:174)
at org.apache.http.impl.nio.reactor.DefaultConnectingIOReactor.processEvents(DefaultConnectingIOReactor.java:148)
at org.apache.http.impl.nio.reactor.AbstractMultiworkerIOReactor.execute(AbstractMultiworkerIOReactor.java:351)
at org.apache.http.impl.nio.conn.PoolingNHttpClientConnectionManager.execute(PoolingNHttpClientConnectionManager.java:221)
at org.apache.http.impl.nio.client.CloseableHttpAsyncClientBase$1.run(CloseableHttpAsyncClientBase.java:64)
... 1 common frames omitted
I have double checked my url, port and credentials. How do i solve this problem?
In springboot 3 just creating ClientConfiguration bean is not enough, the configuration class needs to extend the class ElasticsearchConfiguration as well.
#Configuration
#Slf4j
#EnableElasticsearchRepositories(basePackages = "com....elastic")
public class ElasticConfig extends ElasticsearchConfiguration {
#Override
public ClientConfiguration clientConfiguration() {
ClientConfiguration clientConfiguration = ClientConfiguration.builder()
.connectedTo("192.168.19.23:9200")
.usingSsl()
.withConnectTimeout(Duration.ofSeconds(5))
.withSocketTimeout(Duration.ofSeconds(3))
.withBasicAuth("elastic", "abc")
.build();
return clientConfiguration;
}
}
With this configuration ElasticsearchOperations, ElasticsearchClient and RestClient can be autowired as well.
Edit (P.J.Meisch): This is documented as well: https://docs.spring.io/spring-data/elasticsearch/docs/current/reference/html/#elasticsearch.clients.restclient

Spring boot LDAP get memberOf in ODM

I'm currenly building an application using Spring boot LDAP, but have some problems accessing the 'memberOf' property to determine which groups the users belongs to.
I have seen Spring LDAP and MemberOf but I am using the ODM to get the user from LDAP, when trying to add the 'memberOf' property I get the following error:
org.springframework.ldap.odm.core.impl.MetaDataException: Can't determine destination type for field private java.util.ArrayList nl.quintor.afstudeermanagementtool.entitiy.LdapUser.memberOf in class class nl.quintor.afstudeermanagementtool.entitiy.LdapUser
at org.springframework.ldap.odm.core.impl.AttributeMetaData.determineFieldType(AttributeMetaData.java:167) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.odm.core.impl.AttributeMetaData.<init>(AttributeMetaData.java:234) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.odm.core.impl.ObjectMetaData.<init>(ObjectMetaData.java:132) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.odm.core.impl.DefaultObjectDirectoryMapper.addManagedClass(DefaultObjectDirectoryMapper.java:151) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.odm.core.impl.DefaultObjectDirectoryMapper.getEntityData(DefaultObjectDirectoryMapper.java:108) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.odm.core.impl.DefaultObjectDirectoryMapper.filterFor(DefaultObjectDirectoryMapper.java:468) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.core.LdapTemplate.find(LdapTemplate.java:1824) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.core.LdapTemplate.findAll(LdapTemplate.java:1806) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.ldap.core.LdapTemplate.findAll(LdapTemplate.java:1814) ~[spring-ldap-core-2.3.3.RELEASE.jar:2.3.3.RELEASE]
at org.springframework.data.ldap.repository.support.SimpleLdapRepository.findAll(SimpleLdapRepository.java:183) ~[spring-data-ldap-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.data.repository.core.support.ImplementationInvocationMetadata.invoke(ImplementationInvocationMetadata.java:72) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryComposition$RepositoryFragments.invoke(RepositoryComposition.java:382) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryComposition.invoke(RepositoryComposition.java:205) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$ImplementationMethodExecutionInterceptor.invoke(RepositoryFactorySupport.java:550) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.doInvoke(QueryExecutorMethodInterceptor.java:155) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.data.repository.core.support.QueryExecutorMethodInterceptor.invoke(QueryExecutorMethodInterceptor.java:130) ~[spring-data-commons-2.3.9.RELEASE.jar:2.3.9.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:95) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at com.sun.proxy.$Proxy82.findAll(Unknown Source) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:344) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:198) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:139) ~[spring-tx-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212) ~[spring-aop-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at com.sun.proxy.$Proxy82.findAll(Unknown Source) ~[na:na]
at nl.quintor.afstudeermanagementtool.seeders.DatabaseSeeder.seedUserTable(DatabaseSeeder.java:59) ~[classes/:na]
at nl.quintor.afstudeermanagementtool.seeders.DatabaseSeeder.seed(DatabaseSeeder.java:39) ~[classes/:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.context.event.ApplicationListenerMethodAdapter.doInvoke(ApplicationListenerMethodAdapter.java:305) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.event.ApplicationListenerMethodAdapter.processEvent(ApplicationListenerMethodAdapter.java:190) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.event.ApplicationListenerMethodAdapter.onApplicationEvent(ApplicationListenerMethodAdapter.java:153) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.event.SimpleApplicationEventMulticaster.doInvokeListener(SimpleApplicationEventMulticaster.java:172) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.event.SimpleApplicationEventMulticaster.invokeListener(SimpleApplicationEventMulticaster.java:165) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.event.SimpleApplicationEventMulticaster.multicastEvent(SimpleApplicationEventMulticaster.java:139) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.publishEvent(AbstractApplicationContext.java:404) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.publishEvent(AbstractApplicationContext.java:361) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishRefresh(AbstractApplicationContext.java:898) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:554) ~[spring-context-5.2.14.RELEASE.jar:5.2.14.RELEASE]
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:143) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:755) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:747) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:402) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:312) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1247) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1236) ~[spring-boot-2.3.10.RELEASE.jar:2.3.10.RELEASE]
at nl.quintor.afstudeermanagementtool.AfstudeermanagementtoolApplication.main(AfstudeermanagementtoolApplication.java:16) ~[classes/:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:na]
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:na]
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:na]
at java.base/java.lang.reflect.Method.invoke(Method.java:566) ~[na:na]
at org.springframework.boot.devtools.restart.RestartLauncher.run(RestartLauncher.java:49) ~[spring-boot-devtools-2.3.10.RELEASE.jar:2.3.10.RELEASE]
2021-05-18 16:14:16.109 INFO 14468 --- [ restartedMain] j.LocalContainerEntityManagerFactoryBean : Closing JPA EntityManagerFactory for persistence unit 'default'
2021-05-18 16:14:16.112 INFO 14468 --- [ restartedMain] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown initiated...
2021-05-18 16:14:16.139 INFO 14468 --- [ restartedMain] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown completed.
Process finished with exit code 0
The code I'm using is:
#Entry(
objectClasses = { "user, Person", "top", "organizationalPerson" })
public class LdapUser {
private #Id Name id;
private #Attribute(name = "cn") String fullName;
private #Attribute(name = "sAMAccountName") String username;
private #Attribute(name ="memberof", readonly = true)
ArrayList<?> memberOf;
public LdapUser() { }
public LdapUser(String fullName, String username, ArrayList<?> memberOf) {
this.fullName = fullName;
this.username = username;
this.memberOf = memberOf;
}
public String getFullName() {
return fullName;
}
public void setFullName(String fullName) {
this.fullName = fullName;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public ArrayList<?> getMemberOf() {
return memberOf;
}
public void setMemberOf(ArrayList<?> memberOf) {
this.memberOf = memberOf;
}
}
This appears to be a "shortcoming" common to reflection-based object mapping frameworks in Java.
Annotating Java class fields with #Attribute only works if the annotated field is a concrete type: that is why the annotation works with ArrayList<String> but not List<String> or ArrayList<?>, because in the latter two cases the object mapper would have to 'guess' which concrete type to use when populating that field. In other words, the object mapper cannot call new List<String>(), so it throws an exception.
You can read about a similar problem affecting the JPA ORM standard. JPA appears to have a workaround by providing the targetEntity attribute element, but this is only present on some of their annotations (like #ManyToMany), and not on #Column, which is roughly equivalent to #Attribute here.

Autowried in hibernate constraintvalidator returns nullexception

After looking around, I couldn't find any good solution to this.
My autowired didn't work as expected where it returns null. I've autowired this particular class in other classes and it works so it only doesn't work in constraintvalidator classes.
Error
java.lang.IllegalStateException: Failed to execute CommandLineRunner
at
org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:798)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
org.springframework.boot.SpringApplication.callRunners(SpringApplication.java:779)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:322)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:1237)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:1226)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
com.Alex.Mains.JpaApplication.main(JpaApplication.java:21)
~[classes/:na] Caused by:
org.springframework.transaction.TransactionSystemException: Could not
commit JPA transaction; nested exception is
javax.persistence.RollbackException: Error while committing the
transaction at
org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:543)
~[spring-orm-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:743)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:711)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.transaction.interceptor.TransactionAspectSupport.commitTransactionAfterReturning(TransactionAspectSupport.java:632)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:386)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:118)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:139)
~[spring-tx-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.data.jpa.repository.support.CrudMethodMetadataPostProcessor$CrudMethodMetadataPopulatingMethodInterceptor.invoke(CrudMethodMetadataPostProcessor.java:178)
~[spring-data-jpa-2.3.1.RELEASE.jar:2.3.1.RELEASE] at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:95)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212)
~[spring-aop-5.2.7.RELEASE.jar:5.2.7.RELEASE] at
com.sun.proxy.$Proxy93.save(Unknown Source) ~[na:na] at
com.Alex.Mains.UserRepositoryCommandLineRunner.run(UserRepositoryCommandLineRunner.java:26)
~[classes/:na] at
org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:795)
~[spring-boot-2.3.1.RELEASE.jar:2.3.1.RELEASE] ... 5 common frames
omitted Caused by: javax.persistence.RollbackException: Error while
committing the transaction at
org.hibernate.internal.ExceptionConverterImpl.convertCommitException(ExceptionConverterImpl.java:81)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.engine.transaction.internal.TransactionImpl.commit(TransactionImpl.java:104)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:534)
~[spring-orm-5.2.7.RELEASE.jar:5.2.7.RELEASE] ... 21 common frames
omitted Caused by: javax.validation.ValidationException: HV000028:
Unexpected exception during isValid call. at
org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateSingleConstraint(ConstraintTree.java:186)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.constraintvalidation.SimpleConstraintTree.validateConstraints(SimpleConstraintTree.java:62)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateConstraints(ConstraintTree.java:75)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.metadata.core.MetaConstraint.doValidateConstraint(MetaConstraint.java:130)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.metadata.core.MetaConstraint.validateConstraint(MetaConstraint.java:123)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validateMetaConstraint(ValidatorImpl.java:555)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForSingleDefaultGroupElement(ValidatorImpl.java:518)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForDefaultGroup(ValidatorImpl.java:488)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validateConstraintsForCurrentGroup(ValidatorImpl.java:450)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validateInContext(ValidatorImpl.java:400)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.validator.internal.engine.ValidatorImpl.validate(ValidatorImpl.java:172)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final] at
org.hibernate.cfg.beanvalidation.BeanValidationEventListener.validate(BeanValidationEventListener.java:116)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.cfg.beanvalidation.BeanValidationEventListener.onPreInsert(BeanValidationEventListener.java:80)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.action.internal.EntityInsertAction.preInsert(EntityInsertAction.java:227)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.action.internal.EntityInsertAction.execute(EntityInsertAction.java:100)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.engine.spi.ActionQueue.executeActions(ActionQueue.java:604)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.engine.spi.ActionQueue.lambda$executeActions$1(ActionQueue.java:478)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
java.base/java.util.LinkedHashMap.forEach(LinkedHashMap.java:723)
~[na:na] at
org.hibernate.engine.spi.ActionQueue.executeActions(ActionQueue.java:475)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.event.internal.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:348)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.event.internal.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:40)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.event.service.internal.EventListenerGroupImpl.fireEventOnEachListener(EventListenerGroupImpl.java:102)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.internal.SessionImpl.doFlush(SessionImpl.java:1360)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.internal.SessionImpl.managedFlush(SessionImpl.java:451)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.internal.SessionImpl.flushBeforeTransactionCompletion(SessionImpl.java:3210)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.internal.SessionImpl.beforeTransactionCompletion(SessionImpl.java:2378)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.engine.jdbc.internal.JdbcCoordinatorImpl.beforeTransactionCompletion(JdbcCoordinatorImpl.java:447)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.beforeCompletionCallback(JdbcResourceLocalTransactionCoordinatorImpl.java:183)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.access$300(JdbcResourceLocalTransactionCoordinatorImpl.java:40)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl$TransactionDriverControlImpl.commit(JdbcResourceLocalTransactionCoordinatorImpl.java:281)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] at
org.hibernate.engine.transaction.internal.TransactionImpl.commit(TransactionImpl.java:101)
~[hibernate-core-5.4.17.Final.jar:5.4.17.Final] ... 22 common frames
omitted Caused by: java.lang.NullPointerException: null at
com.Alex.Validations.EmailValidator.isValid(EmailValidator.java:26)
~[classes/:na] at
com.Alex.Validations.EmailValidator.isValid(EmailValidator.java:1)
~[classes/:na] at
org.hibernate.validator.internal.engine.constraintvalidation.ConstraintTree.validateSingleConstraint(ConstraintTree.java:180)
~[hibernate-validator-6.1.5.Final.jar:6.1.5.Final]
UserService class
#Service
public class UserService {
#Autowired
private UserRepository userRep;
public void addUser(User user) {
userRep.save(user);
}
public void deleteUser(long userId) {
userRep.deleteById(userId);
}
public List<User> retrieveAllUsers(){
Iterable<User>temp =userRep.findAll();
List<User>allUsers = null;
temp.forEach(allUsers::add);
return allUsers;
}
public boolean searchByEmail(String email) {
return userRep.findByEmail(email);
}
public void updateUser(User user) {
userRep.save(user);
}
}
Annotation interface class
#Target(ElementType.FIELD)
//When will the annotation be processed compilation, runtime etc
#Retention(RetentionPolicy.RUNTIME)
//Where is the logic
#Constraint(validatedBy = EmailValidator.class)
#Documented
public #interface ValidEmail {
//Error message
String message() default "Invalid email";
//Required for annotation
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
Annotation logic class
public class EmailValidator implements ConstraintValidator<ValidEmail, String> {
#Autowired
private UserService service;
//Actual place to place the logic to check if the data is valid or not
#Override
public boolean isValid(String email, ConstraintValidatorContext context) {
if (email == null) {
return false;
}
List<User> users = service.retrieveAllUsers();
if (users.size() > 0) {
return Pattern.matches("(?:[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*|\"(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21\\x23-\\x5b\\x5d-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])*\")#(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\\[(?:(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9]))\\.){3}(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9])|[a-z0-9-]*[a-z0-9]:(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21-\\x5a\\x53-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])+)\\])", email)
&& service.searchByEmail(email);
}
else {
return Pattern.matches("(?:[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*|\"(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21\\x23-\\x5b\\x5d-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])*\")#(?:(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?|\\[(?:(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9]))\\.){3}(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9])|[a-z0-9-]*[a-z0-9]:(?:[\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x21-\\x5a\\x53-\\x7f]|\\\\[\\x01-\\x09\\x0b\\x0c\\x0e-\\x7f])+)\\])", email);
}
}
#Override
public void initialize(ValidEmail validEmail) {
validEmail.message();
}
}
Main
#SpringBootApplication
#ComponentScan(basePackages = {
"com.Alex.Mains", "com.Alex.UserPackage", "com.Alex.Flights", "com.Alex.Security"
})
#EntityScan( basePackages = {"com.Alex.UserPackage", "com.Alex.Flights"})
#EnableJpaRepositories({"com.Alex.UserPackage", "com.Alex.Flights"})
public class JpaApplication {
public static void main(String[] args) {
SpringApplication.run(JpaApplication.class, args);
}
// #Bean
// public Validator validator(final AutowireCapableBeanFactory beanFactory) {
//
// ValidatorFactory validatorFactory = Validation.byProvider(HibernateValidator.class)
// .configure()
// .constraintValidatorFactory(new SpringConstraintValidatorFactory(beanFactory))
// .buildValidatorFactory();
//
// return validatorFactory.getValidator();
// }
}
Hibernate is calling the validation and it does not know anything about Spring by default so that #Autowired stereotype is not going to be honoured.
If you want to use Spring there, you need to configure Hibernate to be able to resolve the dependency injection properly.
I can't know for sure as you haven't shared a sample we can run but try to add the following configuration:
#Configuration
class HibernateCustomization {
#Bean
public HibernatePropertiesCustomizer hibernatePropertiesCustomizer(ValidatorFactory validatorFactory) {
return (properties) -> {
properties.put(org.hibernate.cfg.AvailableSettings.JPA_VALIDATION_FACTORY, validatorFactory);
};
}
}

spring security data with index issues

trying to use method level security with spring data security.
I have created a sample repo
https://github.com/jayasai470/spring-data-security-sample/
when #Indexed is commented everything works fine and I can see in mongo debug logs that
for the spel query #Query("{tenantId: ?#{principal.tenantId}}") tenantId is properly injected
but when I try to include the #Indexed annotation server fails to start. Mongo template threw an exception with Authentication object is null
// my entity class
#Data
#Document(collection = "userprofiles")
public class UserProfile {
#Id
#Field("_id")
private String id;
#Email(message = "not a valid email")
#Indexed(unique = true, name = "email_1", background = true)
private String email;
private String tenantId;
}
//repository
#Repository
public interface UserProfileRepository extends
PagingAndSortingRepository<UserProfile, String> {
UserProfile findOneByEmail(String email);
#Query("{tenantId: ?#{principal.tenantId}}")
List<UserProfile> findAllByTenantId();
}
// registered a bean of SecurityEvaluationContextExtension
public class MongoSecurityEvaluationContextExtension extends
SecurityEvaluationContextExtension {
#Override
public String getExtensionId() {
return "security";
}
#Override
public Map<String, Object> getProperties() {
return Collections.singletonMap("principal", (UserProfile)
SecurityContextHolder.getContext().getAuthentication().getPrincipal());
}
}
//web security config
#EnableWebSecurity
#EnableGlobalMethodSecurity(prePostEnabled = true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
#Bean
public SecurityEvaluationContextExtension
securityEvaluationContextExtension() {
return new MongoSecurityEvaluationContextExtension();
}
}
Above code works fine if we remove the #indexed annotation. if indexing is enabled then server fails to start
below is the stack-trace
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.data.mongodb.core.MongoTemplate]: Factory method 'mongoTemplate' threw exception; nested exception is java.lang.IllegalArgumentException: Authentication object cannot be null
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:185) ~[spring-beans-5.2.2.RELEASE.jar:5.2.2.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:651) ~[spring-beans-5.2.2.RELEASE.jar:5.2.2.RELEASE]
... 67 common frames omitted
Caused by: java.lang.IllegalArgumentException: Authentication object cannot be null
at org.springframework.security.access.expression.SecurityExpressionRoot.<init>(SecurityExpressionRoot.java:61) ~[spring-security-core-5.2.1.RELEASE.jar:5.2.1.RELEASE]
at org.springframework.security.data.repository.query.SecurityEvaluationContextExtension$1.<init>(SecurityEvaluationContextExtension.java:108) ~[spring-security-data-5.2.1.RELEASE.jar:5.2.1.RELEASE]
at org.springframework.security.data.repository.query.SecurityEvaluationContextExtension.getRootObject(SecurityEvaluationContextExtension.java:108) ~[spring-security-data-5.2.1.RELEASE.jar:5.2.1.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider$EvaluationContextExtensionAdapter.<init>(ExtensionAwareEvaluationContextProvider.java:369) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider.lambda$toAdapters$2(ExtensionAwareEvaluationContextProvider.java:159) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193) ~[na:1.8.0_221]
at java.util.stream.SortedOps$SizedRefSortingSink.end(SortedOps.java:352) ~[na:1.8.0_221]
at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:483) ~[na:1.8.0_221]
at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:472) ~[na:1.8.0_221]
at java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:708) ~[na:1.8.0_221]
at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234) ~[na:1.8.0_221]
at java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:499) ~[na:1.8.0_221]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider.toAdapters(ExtensionAwareEvaluationContextProvider.java:160) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider.access$000(ExtensionAwareEvaluationContextProvider.java:65) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider$ExtensionAwarePropertyAccessor.<init>(ExtensionAwareEvaluationContextProvider.java:182) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider.getEvaluationContext(ExtensionAwareEvaluationContextProvider.java:110) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.spel.ExtensionAwareEvaluationContextProvider.getEvaluationContext(ExtensionAwareEvaluationContextProvider.java:64) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mapping.model.BasicPersistentEntity.getEvaluationContext(BasicPersistentEntity.java:528) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.mapping.BasicMongoPersistentEntity.getEvaluationContext(BasicMongoPersistentEntity.java:182) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.getEvaluationContextForProperty(MongoPersistentEntityIndexResolver.java:525) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.pathAwareIndexName(MongoPersistentEntityIndexResolver.java:584) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.createIndexDefinition(MongoPersistentEntityIndexResolver.java:443) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.createIndexDefinitionHolderForProperty(MongoPersistentEntityIndexResolver.java:213) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.potentiallyAddIndexForProperty(MongoPersistentEntityIndexResolver.java:145) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.lambda$resolveIndexForEntity$1(MongoPersistentEntityIndexResolver.java:129) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mapping.model.BasicPersistentEntity.doWithProperties(BasicPersistentEntity.java:355) ~[spring-data-commons-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.resolveIndexForEntity(MongoPersistentEntityIndexResolver.java:128) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexResolver.resolveIndexFor(MongoPersistentEntityIndexResolver.java:104) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexCreator.checkForAndCreateIndexes(MongoPersistentEntityIndexCreator.java:140) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexCreator.checkForIndexes(MongoPersistentEntityIndexCreator.java:130) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexCreator.<init>(MongoPersistentEntityIndexCreator.java:95) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.index.MongoPersistentEntityIndexCreator.<init>(MongoPersistentEntityIndexCreator.java:72) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.data.mongodb.core.MongoTemplate.<init>(MongoTemplate.java:275) ~[spring-data-mongodb-2.2.3.RELEASE.jar:2.2.3.RELEASE]
at org.springframework.boot.autoconfigure.data.mongo.MongoDbFactoryDependentConfiguration.mongoTemplate(MongoDbFactoryDependentConfiguration.java:63) ~[spring-boot-autoconfigure-2.2.2.RELEASE.jar:2.2.2.RELEASE]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_221]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_221]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_221]
at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_221]
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:154) ~[spring-beans-5.2.2.RELEASE.jar:5.2.2.RELEASE]
... 68 common frames omitted
Process finished with exit code 1

Can't configure EntityManager with Transactional using Spring Boot

Currently I am writing Spring boot application to move data from Database in source A to another Database in source B. To do so, I am trying to configure Spring with two datasource and tried to retrive data from source A concurrently and insert to source B. I could retrieve data from source A but the problem is that I could not insert those data to source B. It seems like I didn't configure transactional correctly with EntityManager. Please check my below code and help me figure out this.
Here is my datasource configuration class:
#Configuration
#EnableJpaRepositories(
basePackages = ["com.gdce.xgen.repo.psql"],
entityManagerFactoryRef = "psqlEntityManager",
transactionManagerRef = "psqlTransactional")
#EnableTransactionManagement
#ComponentScan("com.gdce.xgen.repo.psql")
class PsqlDataSource {
#Bean("psqlEntityManager")
fun entityManagerFactory(#Qualifier("psqlDataSource1") dataSource: DataSource): LocalContainerEntityManagerFactoryBean {
val em = LocalContainerEntityManagerFactoryBean()
val vendorAdapter: JpaVendorAdapter = HibernateJpaVendorAdapter()
em.dataSource = dataSource
em.jpaVendorAdapter = vendorAdapter
em.setPackagesToScan("com.gdce.xgen.model.psql")
em.setJpaProperties(hibernateProperties())
return em
}
#Bean("psqlDataSource1")
#ConfigurationProperties("psql.datasource.main.configuration")
fun dataSource(#Qualifier("psqlDataSourceProperties") dataSourceProperties: DataSourceProperties): DataSource {
return dataSourceProperties.initializeDataSourceBuilder().type(HikariDataSource::class.java).build()
}
#Bean("psqlDataSourceProperties")
#ConfigurationProperties("psql.datasource.main")
fun dataSourceProperties(): DataSourceProperties {
return DataSourceProperties()
}
#Bean("psqlTransactional")
fun transactionManager(#Qualifier("psqlEntityManager") entityManager: EntityManager, #Qualifier("psqlDataSource1") dataSource: DataSource): PlatformTransactionManager {
val transactionManager = JpaTransactionManager(entityManager.entityManagerFactory)
transactionManager.dataSource = dataSource
return transactionManager
}
private fun hibernateProperties(): Properties {
val hibernateProperties = Properties()
hibernateProperties.setProperty("hibernate.jdbc.lob.non_contextual_creation", "true")
hibernateProperties.setProperty("hibernate.show_sql", "true")
hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "update")
hibernateProperties.setProperty("hibernate.jdbc.batch_size", "40000")
hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.PostgreSQLDialect")
hibernateProperties.setProperty("hibernate.connection.pool_size", "20")
hibernateProperties.setProperty("hibernate.order_inserts", "true")
hibernateProperties.setProperty("hibernate.order_updates", "true")
// hibernateProperties.setProperty("hibernate.format_sql", "true")
return hibernateProperties
}
}
Here is the class I use to insert data into destination data source
#Service
class InsertRepo {
#Qualifier("psqlEntityManager")
// #Autowired // also tried this but not working and saw many people use #PersistenceContext and tried it too
#PersistenceContext
private lateinit var entityManager: EntityManager
fun migrate(records: ArrayList<Any>) {
records.parallelStream().forEach { record ->
run {
entityManager.persist(record)
}
}
}
}
Here an error output:
Exception in thread "DefaultDispatcher-worker-1" javax.persistence.TransactionRequiredException: No EntityManager with actual transaction available for current thread - cannot reliably process 'persist' call
at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:298)
at com.sun.proxy.$Proxy83.persist(Unknown Source)
at com.gdce.xgen.repo.psql.InsertRepo$migrate$1.accept(InsertRepo.kt:18)
at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183)
at java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1654)
at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
at java.base/java.util.stream.ForEachOps$ForEachTask.compute(ForEachOps.java:290)
at java.base/java.util.concurrent.CountedCompleter.exec(CountedCompleter.java:746)
at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290)
at java.base/java.util.concurrent.ForkJoinTask.doInvoke(ForkJoinTask.java:408)
at java.base/java.util.concurrent.ForkJoinTask.invoke(ForkJoinTask.java:736)
at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateParallel(ForEachOps.java:159)
at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateParallel(ForEachOps.java:173)
at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:233)
at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)
at java.base/java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:661)
at com.gdce.xgen.repo.psql.InsertRepo.migrate(InsertRepo.kt:16)
at com.gdce.xgen.controller.TestController$find$$inlined$map$lambda$1.invokeSuspend(TestController.kt:46)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)
If i modify my InsertRepo to:
#Service
class InsertRepo {
#Qualifier("psqlEntityManager")
#PersistenceContext
private lateinit var entityManager: EntityManager
#javax.transaction.Transactional
fun migrate(records: ArrayList<Any>) {
records.parallelStream().forEach { record ->
run {
entityManager.persist(record)
}
}
}
}
Then I got this error log:
Exception in thread "DefaultDispatcher-worker-1" javax.persistence.TransactionRequiredException
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:490)
at java.base/java.util.concurrent.ForkJoinTask.getThrowableException(ForkJoinTask.java:603)
at java.base/java.util.concurrent.ForkJoinTask.reportException(ForkJoinTask.java:678)
at java.base/java.util.concurrent.ForkJoinTask.invoke(ForkJoinTask.java:737)
at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateParallel(ForEachOps.java:159)
at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateParallel(ForEachOps.java:173)
at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:233)
at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)
at java.base/java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:661)
at com.gdce.xgen.repo.psql.InsertRepo.migrate(InsertRepo.kt:18)
at com.gdce.xgen.repo.psql.InsertRepo$$FastClassBySpringCGLIB$$aa68e733.invoke(<generated>)
at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:218)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:769)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:353)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:99)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:689)
at com.gdce.xgen.repo.psql.InsertRepo$$EnhancerBySpringCGLIB$$85ac330b.migrate(<generated>)
at com.gdce.xgen.controller.TestController$find$$inlined$map$lambda$1.invokeSuspend(TestController.kt:46)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)
Caused by: javax.persistence.TransactionRequiredException: No EntityManager with actual transaction available for current thread - cannot reliably process 'persist' call
I have also tried to use #org.springframework.transaction.annotation.Transactional then i got this error log:
Exception in thread "DefaultDispatcher-worker-1" javax.persistence.TransactionRequiredException
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:490)
at java.base/java.util.concurrent.ForkJoinTask.getThrowableException(ForkJoinTask.java:603)
at java.base/java.util.concurrent.ForkJoinTask.reportException(ForkJoinTask.java:678)
at java.base/java.util.concurrent.ForkJoinTask.invoke(ForkJoinTask.java:737)
at java.base/java.util.stream.ForEachOps$ForEachOp.evaluateParallel(ForEachOps.java:159)
at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateParallel(ForEachOps.java:173)
at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:233)
at java.base/java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:497)
at java.base/java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:661)
at com.gdce.xgen.repo.psql.InsertRepo.migrate(InsertRepo.kt:17)
at com.gdce.xgen.repo.psql.InsertRepo$$FastClassBySpringCGLIB$$aa68e733.invoke(<generated>)
at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:218)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:769)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:353)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:99)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:689)
at com.gdce.xgen.repo.psql.InsertRepo$$EnhancerBySpringCGLIB$$82673045.migrate(<generated>)
at com.gdce.xgen.controller.TestController$find$$inlined$map$lambda$1.invokeSuspend(TestController.kt:46)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)
Caused by: javax.persistence.TransactionRequiredException: No EntityManager with actual transaction available for current thread - cannot reliably process 'persist' call
at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:298)
at com.sun.proxy.$Proxy83.persist(Unknown Source)
at com.gdce.xgen.repo.psql.InsertRepo$migrate$1.accept(InsertRepo.kt:19)
at java.base/java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:183)
at java.base/java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1654)
at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
at java.base/java.util.stream.ForEachOps$ForEachTask.compute(ForEachOps.java:290)
at java.base/java.util.concurrent.CountedCompleter.exec(CountedCompleter.java:746)
at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:290)
at java.base/java.util.concurrent.ForkJoinPool$WorkQueue.topLevelExec(ForkJoinPool.java:1020)
at java.base/java.util.concurrent.ForkJoinPool.scan(ForkJoinPool.java:1656)
at java.base/java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1594)
at java.base/java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:177)
I have tried to get transactional from entityManager but i got some error:
Exception in thread "DefaultDispatcher-worker-1" java.lang.IllegalStateException: Not allowed to create transaction on shared EntityManager - use Spring transactions or EJB CMT instead
at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:264)
at com.sun.proxy.$Proxy83.getTransaction(Unknown Source)
at com.gdce.xgen.repo.psql.InsertRepo.migrate(InsertRepo.kt:17)
at com.gdce.xgen.repo.psql.InsertRepo$$FastClassBySpringCGLIB$$aa68e733.invoke(<generated>)
at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:218)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:769)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:353)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:99)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:186)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:747)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:689)
at com.gdce.xgen.repo.psql.InsertRepo$$EnhancerBySpringCGLIB$$3c37a126.migrate(<generated>)
at com.gdce.xgen.controller.TestController$find$$inlined$map$lambda$1.invokeSuspend(TestController.kt:46)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(Dispatched.kt:241)
at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:594)
at kotlinx.coroutines.scheduling.CoroutineScheduler.access$runSafely(CoroutineScheduler.kt:60)
at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:740)

Resources