Hi, I was making some project based on 3.0.0 M4, with Kotlin.
As preparing GA, I tried to replace M4 to M5, and I have encountered unexpected exception when application is launched, which was not the problem from M4. I figured out where the problem is, but I do not know how to solve this. The origin of problem is inside of Jpa Entity, when I use @Convert annotation for converting list of enum to single String. below code worked well without any problem from M4.
enum class BalanceUsageType {
DEPOSIT,
COMMISSION,
GENERAL,
}
@Converter
class BalanceUsageTypeListToStringConverter : AttributeConverter<List<BalanceUsageType>, String?> {
override fun convertToDatabaseColumn(attribute: List<BalanceUsageType>): String? {
if (attribute.isEmpty()) {
return null
}
val listOfString = attribute.map { it.toString() }
return listOfString.joinToString(DELIMITER)
}
override fun convertToEntityAttribute(dbData: String?): List<BalanceUsageType> {
return dbData?.split(DELIMITER)?.map { BalanceUsageType.valueOf(it) } ?: emptyList()
}
companion object {
private const val DELIMITER = ","
}
}
@Entity
@Table(name = "balance")
class BalanceJpaEntity(
@Id
@GeneratedValue
var id: Long = 0,
@Column(nullable = false)
@Audited
var amount: BigDecimal,
@Column
@Enumerated(EnumType.STRING)
var type: BalanceType,
@Column
@Convert(converter = BalanceUsageTypeListToStringConverter::class)
var usageType: List<BalanceUsageType>,
@Column(nullable = false)
var ownerId: Long,
@Column(nullable = false)
var nickname: String,
@Column(nullable = false)
@Audited
var lastLedgerDetailId: Long,
@Column(nullable = false)
@Audited
var deleted: Boolean = false,
) : JpaEntity<Balance> {
@TenantId
lateinit var companyCode: String
constructor(balance: Balance) : this(
balance.id,
balance.amount,
balance.type,
balance.usageType,
balance.ownerId,
balance.nickname,
balance.lastLedgerDetailId,
)
override fun update(domainEntity: Balance) {
// this.id = domainEntity.id
this.amount = domainEntity.amount
// this.ownerId = domainEntity.ownerId
// this.usageType = domainEntity.usageType
this.nickname = domainEntity.nickname
this.lastLedgerDetailId = domainEntity.lastLedgerDetailId
}
override fun toDomainEntity(): Balance {
return Balance(
id,
amount,
type,
usageType,
ownerId,
nickname,
lastLedgerDetailId
)
}
}
below is log for the error
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'entityManagerFactory' defined in class path resource [org/springframework/boot/autoconfigure/orm/jpa/HibernateJpaConfiguration.class]: class sun.reflect.generics.reflectiveObjects.WildcardTypeImpl cannot be cast to class java.lang.reflect.ParameterizedType (sun.reflect.generics.reflectiveObjects.WildcardTypeImpl and java.lang.reflect.ParameterizedType are in module java.base of loader 'bootstrap')
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1754) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:599) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:521) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:326) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:324) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:1141) ~[spring-context-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:916) ~[spring-context-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:592) ~[spring-context-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:146) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:751) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:442) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:314) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1323) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1312) ~[spring-boot-3.0.0-M5.jar:3.0.0-M5]
at com.soplus.pilot.PilotApplicationKt.main(PilotApplication.kt:63) ~[main/:na]
Caused by: java.lang.ClassCastException: class sun.reflect.generics.reflectiveObjects.WildcardTypeImpl cannot be cast to class java.lang.reflect.ParameterizedType (sun.reflect.generics.reflectiveObjects.WildcardTypeImpl and java.lang.reflect.ParameterizedType are in module java.base of loader 'bootstrap')
at org.hibernate.type.descriptor.java.spi.RegistryHelper.determineJavaTypeClass(RegistryHelper.java:114) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.RegistryHelper.createTypeDescriptor(RegistryHelper.java:90) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.RegistryHelper.createTypeDescriptor(RegistryHelper.java:43) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.lambda$resolveDescriptor$1(JavaTypeRegistry.java:154) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.resolveDescriptor(JavaTypeRegistry.java:127) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.resolveDescriptor(JavaTypeRegistry.java:133) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.CollectionJavaType.createJavaType(CollectionJavaType.java:66) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.lambda$resolveDescriptor$1(JavaTypeRegistry.java:140) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.resolveDescriptor(JavaTypeRegistry.java:127) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.resolveDescriptor(JavaTypeRegistry.java:133) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.type.descriptor.java.spi.JavaTypeRegistry.getDescriptor(JavaTypeRegistry.java:73) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.mapping.BasicValue.buildResolution(BasicValue.java:400) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.mapping.BasicValue.resolve(BasicValue.java:315) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.mapping.BasicValue.resolve(BasicValue.java:305) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.boot.internal.InFlightMetadataCollectorImpl.lambda$processValueResolvers$4(InFlightMetadataCollectorImpl.java:1766) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at java.base/java.util.ArrayList.removeIf(ArrayList.java:1682) ~[na:na]
at java.base/java.util.ArrayList.removeIf(ArrayList.java:1660) ~[na:na]
at org.hibernate.boot.internal.InFlightMetadataCollectorImpl.processValueResolvers(InFlightMetadataCollectorImpl.java:1765) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.boot.internal.InFlightMetadataCollectorImpl.processSecondPasses(InFlightMetadataCollectorImpl.java:1751) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.boot.model.process.spi.MetadataBuildingProcess.complete(MetadataBuildingProcess.java:300) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl.metadata(EntityManagerFactoryBuilderImpl.java:1350) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl.build(EntityManagerFactoryBuilderImpl.java:1421) ~[hibernate-core-6.1.3.Final.jar:6.1.3.Final]
at org.springframework.orm.jpa.vendor.SpringHibernateJpaPersistenceProvider.createContainerEntityManagerFactory(SpringHibernateJpaPersistenceProvider.java:66) ~[spring-orm-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean.createNativeEntityManagerFactory(LocalContainerEntityManagerFactoryBean.java:376) ~[spring-orm-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.buildNativeEntityManagerFactory(AbstractEntityManagerFactoryBean.java:409) ~[spring-orm-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.afterPropertiesSet(AbstractEntityManagerFactoryBean.java:396) ~[spring-orm-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean.afterPropertiesSet(LocalContainerEntityManagerFactoryBean.java:352) ~[spring-orm-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1800) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1750) ~[spring-beans-6.0.0-M6.jar:6.0.0-M6]
... 16 common frames omitted
Thanks in advance!
Comment From: wilkinsona
I would guess that this is a regression in Hibernate. Boot 3.0.0-M4 uses Hibernate 6.1.1 whereas M5 uses 6.1.3. Can you try Boot M5 with Hibernate 6.1.1?
Comment From: YoungjeShin
I just tried M5 with Hibernate 6.1.1 (by changing jar), it worked very well.. so this got to be reported to Hibernate-orm side right?
Comment From: wilkinsona
Thanks for giving it a try. Yes, this should be reported to the Hibernate team.