1

swipe新しいオブジェクト を永続化しようとすると、次の例外が発生します。javax.persistence.PersistenceException: org.hibernate.PersistentObjectException: detached entity passed to persist: org.munch.database.models.bunch.Munch

これが私が実行しているコードです:

databaseExecutor.executeAndRollbackOnFailure { entityManager ->
        munch.swipes.forEach {
            if (it.swipeIdKey.munchId != null) {
                entityManager.persist(it)
            } else if (it.updated) {
                entityManager.merge(it)
            }
        }
        entityManager.transaction.commit()
    }

また、参照用にエンティティを以下に貼り付けました。がentityManager.persist(it)呼び出されると、上記のエラーがスローされます。何らかの理由OneToManyで、エンティティの側面も保持しようとしていますが、機能しません。CascadeTypes両方の配列が空であることを確認したので、Swipe呼び出したものだけentityManager.persist()をdbに書き込む必要があることを理解しています。

操作で置き換えるpersistmerge成功しますが、マージにより、休止状態が追加selectの と のMunchを生成しますがselectSwipeこれは不要な操作です。Munchただし、マージは、更新操作を2 つの select ステートメントと 1 つの挿入のみにカスケードしているようには見えません。

要約すると、Hibernate はPersist操作をカスケードしてはならない場合にカスケードしているようです。解決策はmerge代わりに使用するpersistことですが、使用する1 insertと、merge結果として2 selects + 1 insert

ネイティブクエリを実行して挿入/更新する以外のアイデアはありませんが、可能であれば避けたいと思います。

ここに私のエンティティがあります:

Munch


@Entity
@TypeDefs(
    TypeDef(
        name = "list-array",
        typeClass = ListArrayType::class
    )
)
data class Munch(
    @Column
    val name: String,
    @OneToMany(
        fetch = FetchType.LAZY,
        mappedBy = "munch",
    )
    val swipes: MutableList<Swipe> = mutableListOf(),
) {
    @Id
    @GenericGenerator(name = "generator", strategy = "uuid")
    @GeneratedValue(generator = "generator")
    lateinit var munchId: String

    fun addSwipe(swipe: Swipe) {
        swipes.add(swipe)
        swipe.munch = this
    }
}

Swipe

@Entity
data class Swipe(
    @EmbeddedId
    val swipeIdKey: SwipeIdKey,
    @Column(nullable = true)
    val liked: Boolean,
) : Serializable {
    @ManyToOne(fetch = FetchType.LAZY)
    @JoinColumn(name = "munchId")
    @MapsId("munchId")
    lateinit var munch: Munch

    @Transient
    var updated = false

SwipeIdKey

@Embeddable
class SwipeIdKey : Serializable {

    @Column(nullable = false)
    lateinit var restaurantId: String

    @Column(nullable = true)
    lateinit var userId: String

    @Column(nullable = true)
    var munchId: String? = null
}
4

1 に答える 1