调用persist()方法时,将Hibernate 6 PropertyAccessException转换为JPA持久性异常时出错

z31licg0  于 2023-01-05  发布在  其他
关注(0)|答案(1)|浏览(112)

我试图用Ktor 2.2.1(Kotlin 1.8)和Hibernate 6构建一个小Web应用程序。当我试图保存一个实体(在内存数据库中的H2 sql,v2.1.214中)时,我得到这个错误:

Exception in thread "main" jakarta.persistence.PersistenceException: Converting `org.hibernate.property.access.spi.PropertyAccessException` to JPA `PersistenceException` : Error accessing field [private java.lang.Long com.example.models.jpa.UserDto.id] by reflection for persistent property [com.example.models.jpa.UserDto#id] : com.example.models.jpa.UserDto@32ba5c65
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:165)
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:175)
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:182)
    at org.hibernate.internal.SessionImpl.firePersist(SessionImpl.java:743)
    at org.hibernate.internal.SessionImpl.persist(SessionImpl.java:721)
    at com.example.models.H2DatabaseFactory.init(H2DatabaseFactory.kt:27)
    at com.example.ApplicationKt.module(Application.kt:11)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:566)
    at kotlin.reflect.jvm.internal.calls.CallerImpl$Method.callMethod(CallerImpl.kt:97)
    at kotlin.reflect.jvm.internal.calls.CallerImpl$Method$Static.call(CallerImpl.kt:106)
    at kotlin.reflect.jvm.internal.KCallableImpl.call(KCallableImpl.kt:108)
    at kotlin.reflect.jvm.internal.KCallableImpl.callDefaultMethod$kotlin_reflection(KCallableImpl.kt:159)
    at kotlin.reflect.jvm.internal.KCallableImpl.callBy(KCallableImpl.kt:112)
    at io.ktor.server.engine.internal.CallableUtilsKt.callFunctionWithInjection(CallableUtils.kt:119)
    at io.ktor.server.engine.internal.CallableUtilsKt.executeModuleFunction(CallableUtils.kt:36)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading$launchModuleByName$1.invoke(ApplicationEngineEnvironmentReloading.kt:331)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading$launchModuleByName$1.invoke(ApplicationEngineEnvironmentReloading.kt:330)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.avoidingDoubleStartupFor(ApplicationEngineEnvironmentReloading.kt:355)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.launchModuleByName(ApplicationEngineEnvironmentReloading.kt:330)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.access$launchModuleByName(ApplicationEngineEnvironmentReloading.kt:32)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading$instantiateAndConfigureApplication$1.invoke(ApplicationEngineEnvironmentReloading.kt:311)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading$instantiateAndConfigureApplication$1.invoke(ApplicationEngineEnvironmentReloading.kt:309)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.avoidingDoubleStartup(ApplicationEngineEnvironmentReloading.kt:337)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.instantiateAndConfigureApplication(ApplicationEngineEnvironmentReloading.kt:309)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.createApplication(ApplicationEngineEnvironmentReloading.kt:150)
    at io.ktor.server.engine.ApplicationEngineEnvironmentReloading.start(ApplicationEngineEnvironmentReloading.kt:276)
    at io.ktor.server.tomcat.TomcatApplicationEngine.start(TomcatApplicationEngine.kt:145)
    at io.ktor.server.tomcat.EngineMain.main(EngineMain.kt:28)
    at com.example.ApplicationKt.main(Application.kt:8)
Caused by: org.hibernate.property.access.spi.PropertyAccessException: Error accessing field [private java.lang.Long com.example.models.jpa.UserDto.id] by reflection for persistent property [com.example.models.jpa.UserDto#id] : com.example.models.jpa.UserDto@32ba5c65
    at org.hibernate.property.access.spi.GetterFieldImpl.get(GetterFieldImpl.java:48)
    at org.hibernate.metamodel.mapping.internal.BasicEntityIdentifierMappingImpl.getIdentifier(BasicEntityIdentifierMappingImpl.java:147)
    at org.hibernate.persister.entity.AbstractEntityPersister.getIdentifier(AbstractEntityPersister.java:5254)
    at org.hibernate.persister.entity.AbstractEntityPersister.isTransient(AbstractEntityPersister.java:4841)
    at org.hibernate.engine.internal.ForeignKeys.isTransient(ForeignKeys.java:293)
    at org.hibernate.event.internal.EntityState.getEntityState(EntityState.java:59)
    at org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:93)
    at org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:53)
    at org.hibernate.event.service.internal.EventListenerGroupImpl.fireEventOnEachListener(EventListenerGroupImpl.java:107)
    at org.hibernate.internal.SessionImpl.firePersist(SessionImpl.java:737)
    ... 28 more
Caused by: java.lang.IllegalArgumentException: Can not set java.lang.Long field com.example.models.jpa.UserDto.id to com.example.models.jpa.UserDto
    at java.base/jdk.internal.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
    at java.base/jdk.internal.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)
    at java.base/jdk.internal.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.java:58)
    at java.base/jdk.internal.reflect.UnsafeObjectFieldAccessorImpl.get(UnsafeObjectFieldAccessorImpl.java:36)
    at java.base/java.lang.reflect.Field.get(Field.java:418)
    at org.hibernate.property.access.spi.GetterFieldImpl.get(GetterFieldImpl.java:44)
    ... 37 more

我的代码:

import org.hibernate.cfg.Configuration

val sessionFactory = Configuration()
            .addAnnotatedClass(UserDto::class.java)
            .buildSessionFactory()

val session = sessionFactory.openSession()
session.beginTransaction()

var userDto = UserDto()
userDto.username = "admin"
session.persist(userDto)   <-- error here!

session.transaction.commit()

用户日期至:

package com.example.models.jpa

import jakarta.persistence.*

@Entity
open class UserDto {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    open var id: Long? = null

    @Column(nullable = false)
    open var username: String = ""
}

当我调用session.createQuery("select u from UserDto u", UserDto::class.java).list()时,一切正常,所以我可以假设与db和所有其他属性的通信都正常。
我的体型. gradle. kts

...

plugins {
    kotlin("jvm") version "1.8.0"
    id("io.ktor.plugin") version "2.2.1"
    id("org.jetbrains.kotlin.plugin.allopen") version "1.8.0"
    id("org.jetbrains.kotlin.plugin.noarg") version "1.8.0"//this will generate no-argument constructors for your Hibernate entities.
    id("org.jetbrains.kotlin.plugin.jpa") version "1.8.0"
}

allOpen {
    annotation("javax.persistence.Entity")
    annotation("javax.persistence.MappedSuperclass")
    annotation("javax.persistence.Embeddable")
    annotation("jakarta.persistence.Entity")
    annotation("jakarta.persistence.MappedSuperclass")
    annotation("jakarta.persistence.Embeddable")
}

...

dependencies {
    implementation("io.ktor:ktor-server-core-jvm:$ktor_version")
    implementation("io.ktor:ktor-server-auth-jvm:$ktor_version")
    implementation("io.ktor:ktor-server-auth-jwt-jvm:$ktor_version")
    implementation("io.ktor:ktor-server-cors-jvm:$ktor_version")
    implementation("io.ktor:ktor-serialization-gson:$ktor_version")
    implementation("io.ktor:ktor-server-openapi:$ktor_version")
    implementation("io.ktor:ktor-server-swagger:$ktor_version")
    implementation("io.ktor:ktor-server-call-logging-jvm:$ktor_version")
    implementation("io.ktor:ktor-server-tomcat-jvm:$ktor_version")
    implementation("ch.qos.logback:logback-classic:$logback_version")
    implementation("io.ktor:ktor-server-config-yaml:$ktor_version")
    //db
    implementation("mysql:mysql-connector-java:8.0.30")
    implementation("org.hibernate:hibernate-core:6.1.6.Final")
    implementation("com.h2database:h2:$h2_version")
}
    • 编辑:**添加我的应用程序. yml
ktor:
    application:
        modules:
            - com.example.ApplicationKt.module
    development: true
    deployment:
        port: 8080
        watch:
            - classes
            - resources
jwt:
    domain: "https://jwt-provider-domain/"
    audience: "jwt-audience"
    realm: "ktor sample app"

我怎么解决这个问题?我犯了什么错误?谢谢

cunj1qz1

cunj1qz11#

我解决了删除application.yml文件中ktor-〉deployment下的watch部分的问题。我添加了这些行,因为我想将autoreload模式添加到我的服务器,我遵循了官方文档。
我仍然不明白为什么watch会产生这个问题。
所以解决办法是:

ktor:
        application:
            modules:
                - com.example.ApplicationKt.module
        development: true
        deployment:
            port: 8080
            watch:
                - classes
                - resources
    jwt:
        domain: "https://jwt-provider-domain/"
        audience: "jwt-audience"
        realm: "ktor sample app"

我还打开了一个bug report

相关问题