hibernatekotlintransient

Hibernate Transient not working in Kotlin


EDIT: Added the whole stack trace

I have an Class "DGuild" with a couple fields in the Table.
I also have an @Transient field which should not appear in the database table.

But since I added the @Transient annotation it crashes with the following error:

org.hibernate.MappingException: Could not get constructor for org.hibernate.persister.entity.SingleTableEntityPersister
    at org.hibernate.persister.internal.PersisterFactoryImpl.createEntityPersister(PersisterFactoryImpl.java:123)
    at org.hibernate.persister.internal.PersisterFactoryImpl.createEntityPersister(PersisterFactoryImpl.java:77)
    at org.hibernate.metamodel.internal.MetamodelImpl.initialize(MetamodelImpl.java:181)
    at org.hibernate.internal.SessionFactoryImpl.<init>(SessionFactoryImpl.java:301)
    at org.hibernate.boot.internal.SessionFactoryBuilderImpl.build(SessionFactoryBuilderImpl.java:469)
    at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:708)
    at eu.dragoncoding.dragonbot.hibernate.HibernateUtils.createSessionFactory(HibernateUtils.kt:75)
    at eu.dragoncoding.dragonbot.hibernate.HibernateUtils.getSessFactory(HibernateUtils.kt:45)
    at eu.dragoncoding.dragonbot.hibernate.HibernateUtils.<clinit>(HibernateUtils.kt:27)
    at eu.dragoncoding.dragonbot.Bot.startUp(Bot.kt:49)
    at eu.dragoncoding.dragonbot.Main.main(Main.kt:19)
Caused by: org.hibernate.InstantiationException: could not instantiate test object : eu.dragoncoding.dragonbot.hibernate.entities.DGuild
    at org.hibernate.engine.internal.UnsavedValueFactory.instantiate(UnsavedValueFactory.java:43)
    at org.hibernate.engine.internal.UnsavedValueFactory.getUnsavedIdentifierValue(UnsavedValueFactory.java:68)
    at org.hibernate.tuple.PropertyFactory.buildIdentifierAttribute(PropertyFactory.java:63)
    at org.hibernate.tuple.entity.EntityMetamodel.<init>(EntityMetamodel.java:140)
    at org.hibernate.persister.entity.AbstractEntityPersister.<init>(AbstractEntityPersister.java:609)
    at org.hibernate.persister.entity.SingleTableEntityPersister.<init>(SingleTableEntityPersister.java:128)
    at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:64)
    at java.base/jdk.internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Constructor.java:500)
    at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:481)
    at org.hibernate.persister.internal.PersisterFactoryImpl.createEntityPersister(PersisterFactoryImpl.java:96)
    ... 10 common frames omitted
Caused by: java.lang.reflect.InvocationTargetException: null
    at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:64)
    at java.base/jdk.internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.base/java.lang.reflect.Constructor.newInstanceWithCaller(Constructor.java:500)
    at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:481)
    at org.hibernate.engine.internal.UnsavedValueFactory.instantiate(UnsavedValueFactory.java:40)
    ... 21 common frames omitted
Caused by: java.lang.NullPointerException: null
    at eu.dragoncoding.dragonbot.managers.music.GuildMusicController.<init>(GuildMusicController.kt:14)
    at eu.dragoncoding.dragonbot.hibernate.entities.DGuild.<init>(DGuild.kt:37)
    ... 27 common frames omitted

My class looks like this:

import eu.dragoncoding.dragonbot.defaultChannelID
import eu.dragoncoding.dragonbot.defaultPrefix
import eu.dragoncoding.dragonbot.hibernate.EntityDao
import eu.dragoncoding.dragonbot.managers.GuildManager.removeGuild
import eu.dragoncoding.dragonbot.managers.music.GuildMusicController
import lombok.Data
import lombok.NoArgsConstructor
import org.slf4j.LoggerFactory
import javax.persistence.*

@Entity
@Data
@NoArgsConstructor
@Table(name = "Guilds")

class DGuild: eu.dragoncoding.dragonbot.structures.Entity {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "ID", nullable = false)
    val id: Long = 0

    @Column(name = "guildID", nullable = false)
    var guildID: Long = defaultChannelID
    @Column(name = "prefix", nullable = false)
    var prefix: String = defaultPrefix
    @Column(name = "isJoined", nullable = false)
    var isJoined: Boolean = true
    @Column(name = "botChannelID", nullable = false)
    var botChannelID: Long = defaultChannelID
    @Column(name = "commandsUsed", nullable = false)
    var commandsUsed: Int = 0

    @Transient
    val musicManager: GuildMusicController = GuildMusicController(this)

    constructor(guild_ID: Long) {
        this.guildID = guild_ID
    }
    constructor()

    fun save() {
        EntityDao.save(this)
    }
    fun update() {
        EntityDao.update(this)
    }

    fun activate() {
        if (!isJoined) {
            isJoined = true
            update()
        }
    }
    fun deactivate() {
        if (isJoined) {
            isJoined = false
            update()
            removeGuild(guildID)
        }
    }

    fun incrementCommands() {
        this.commandsUsed += 1
        update()
    }


}

I tried to apply the @Transient to the @field:, the @get: and the @set:
I also made the class a serializable.

When I remove the field and annotation it works fine.


Solution

  • I made a big mistake at the init...
    I provided a null value to a constructor that allowed none.

    That happened in the line "val musicManager: GuildMusicController = GuildMusicController(this)" where I wanted to use the DGuild object in the GuildMusicController's constructor. The problem was that it wasn't yet initialized (because it still needed the GuildMusicController object), so it was still null.