0

注釈付きのメソッドが返された後product.getName()、id によって読み込まれたエンティティ オブジェクトの値を取得できないのはなぜですか? このようにして製品オブジェクトを取得すると、すべて問題ありません。session.load(product.class,1)@Transactionalsession.createQuery("from Product as product WHERE product.id = 1)

編集

ダオ法

public Product getProduct(Long id) {
return (Product) currentSession().load(Product.class, id);
}

サービス方法

    @Transactional
public Product getProduct(Long id) {
    return productDao.getProduct(id);
}

コントローラ メソッド - JSON を送信するはずですがproduct.getName()、エラーで中断しますorg.hibernate.LazyInitializationException: could not initialize proxy - no Session

    @RequestMapping(value = "/product",headers="Accept=application/json")
public @ResponseBody Product getProduct() {
    Product product = productService.getProduct(new Long(1));
    System.out.println(product.getName());
    return product;
}
4

2 に答える 2

0

初期化されていないコレクションまたはプロキシが Session の範囲外でアクセスされたLazyInitializationException場合、つまり、コレクションを所有しているエンティティまたはプロキシへの参照を持っているエンティティが切り離された状態にある場合、 が Hibernate によってスローされます。

セッションを閉じる前に、プロキシまたはコレクションを初期化する必要がある場合があります。またはなどを呼び出して、初期化を強制できますproduct.getName()。ただし、これはコードの読者を混乱させる可能性があり、一般的なコードには不向きです。

静的メソッドHibernate.initialize()とはHibernate.isInitialized()、遅延初期化されたコレクションまたはプロキシを操作する便利な方法をアプリケーションに提供します。セッションがまだ開いている限りHibernate.initialize(product)、プロキシの初期化を強制します。product

一部のフィールドをイージーロードするように宣言することもできます

@Entity 
public class Product  {

   @Id 
   @GeneratedValue
   private long id;


   @Basic(fetch=EAGER)
   private String name;


} 
于 2012-04-23T20:35:42.623 に答える
-1

でインスタンスを作成するJava code, the instance is considered to be a transient instanceと、そのインスタンスの永続的な状態を管理するメカニズムがありません。ただし、we pass a transient instance to the save, update, or saveOrUpdate method of the Hibernate SessionHibernate がそのインスタンスの永続状態の管理を開始するため、一時インスタンスが永続インスタンスに移行したと見なします。

Hibernate セッションに関連付けられたインスタンスは、永続インスタンスと呼ばれます。

JavaBean を保存または更新することだけが、永続インスタンスを取得する唯一の方法ではありません。get または load メソッドの呼び出し、または HQL または criteria クエリによって Hibernate セッションにロードされた JavaBeans は、永続的なインスタンスと見なされます。 Hibernate セッションによってもデータベースに永続化されます。

Hibernate の制御から解放したいインスタンスがある場合は、いつでも Hibernate セッションの evict メソッドを呼び出して、Hibernate の制御から解放したいインスタンスの名前を渡すことができます。インスタンスの状態が Hibernate セッションによって管理されなくなった場合、それをデタッチされたインスタンスと呼びます。これは、インスタンスがデータベース内に表現を持っている間、Hibernate がインスタンスと基礎となる永続ストアとの同期を維持するために何もしていないためです。 . 実際には、インスタンスはデータベース内の対応する表現から切り離されます。

もちろん、Hibernate を使用する場合、データベースとのやり取りはすべてトランザクションのスコープ内で発生する必要があります。デフォルトでは、save や update などのメソッドを呼び出すとき、データベース内の対応するレコードがいつ更新されるかを完全に確信することはできません。 Hibernate セッションに関連付けられたインスタンスはデータベースに保存されます。もちろん、すべてのデータをデータベースに保存する操作が何らかの理由で失敗する可能性は常にあります。その場合、Hibernate は実行時例外をスローします。

この時点で、現在のトランザクションをロールバックして Hibernate セッションを閉じる以外にできることはあまりありません。この時点で、以前は Hibernate セッションの制御下にあったすべてのインスタンスが切り離されたオブジェクトになり、データベースと同期していない可能性が非常に高くなります。このような場合、いつでも新しいトランザクションを開始し、保存または更新呼び出しを介して Hibernate セッションに再関連付けすることで、切り離されたインスタンスを永続インスタンスに戻すことを試みることができますが、最終的には、おそらくそのほうがよいでしょう。分かりやすいエラー メッセージをクライアント アプリケーションに送信するだけで、要求と応答のサイクルを最初からやり直すことができます。一時的、永続的、および切り離されたオブジェクトについて話すときの意味を簡単に説明します。

于 2012-04-23T20:18:00.227 に答える