web-dev-qa-db-ja.com

Hibernateエンティティをデタッチして、オブジェクトへの変更がデータベースに自動的に保存されないようにすることは可能ですか?

JSONに変換する必要があるHibernateエンティティがあり、エンティティの一部の値を変換する必要がありますが、値を変換すると、これらの値は即座にデータベースに保存されますが、これらの変更をデータベースに保存したくありません。この問題の回避策はありますか?

51
newbie

Session.evict() を呼び出すことにより、エンティティをデタッチできます。

他のオプションは、値の変換前にエンティティの防御コピーを作成するか、そのコードのエンティティの代わりにDTOを使用することです。これらのオプションはJSONへの変換と永続化レイヤーを結合しないため、よりエレガントだと思います。

44
axtavt

StatelessSessionを使用して、エンティティがHibernateセッションにアタッチされることを回避することもできます。

StatelessSession session = sessionFactory.openStatelessSession();

の代わりに

Session session = sessionFactory.getCurrentSession();

通常のHibernateセッションとは異なり、StatelessSessionを閉じることに注意する必要があることに注意してください。

session.close(); // do this after you are done with the session

通常のセッションと比較したもう1つの違いは、StatelessSessionがコレクションを取得できないことです。データ取得専用のSQLQueryの主な目的だと思います。

さまざまなセッションタイプの詳細については、こちらをご覧ください。

http://www.interviewadda.com/difference-between-getcurrentsession-opensession-and-openstatelesssession/

3
yglodt

また、休止状態のエンティティをJSONに変換しています。

セッションを閉じると、オブジェクトを遅延ロードできません。このため、使用できます

hSession.setDefaultReadOnly(true);

jSONが完了したらセッションを閉じます。

3
elkarel
public static <E> E deepClone(E e) {
    ByteArrayOutputStream bo = new ByteArrayOutputStream();
    ObjectOutputStream oo;
    try {
        oo = new ObjectOutputStream(bo);
        oo.writeObject(e);
    } catch (IOException ex) {
        ex.printStackTrace();
    }
    ByteArrayInputStream bi = new ByteArrayInputStream(bo.toByteArray());
    ObjectInputStream oi;
    try {
        oi = new ObjectInputStream(bi);
        return (E) (oi.readObject());
    } catch (IOException ex) {
        ex.printStackTrace();
        return null;
    } catch (ClassNotFoundException ex) {
        ex.printStackTrace();
        return null;
    }
}

最初:deepClone the session pojo
秒:フィールドの変更
その後:やりたいことを何でもします

0
helloworld1970

セッションを閉じます。これによりエンティティがデタッチされ、変更はフラッシュされません。それが不可能な場合は、autoFlushの無効化を検討してください...最も簡単なのは、セッションを閉じて終了することです!

0
stevevls