1

私のエンティティは、次のように簡略化されています。 baseobject と product は抽象的です

xml ファイル マッピングを使用します。抽象クラスを除く各クラスのテーブルと xml ファイルがあります。遅延読み込みを使用しているため、多くのプロキシがあります。奇妙なことにRefresh(obj)、オブジェクトのタイプが Product1Proxy または Product2Proxy でない限り、それらの 1 つを呼び出すと、毎回機能します。次に、「...Proxy の永続化がありません」というエラーが表示されます。

私は何を試しましたか?

  • <mapping assembly="Project.DomainModel"/>App.configに追加します
  • すべての .hbm.xml ファイルが埋め込みリソースであるかどうかを確認しました (そうです)
  • 私のクラスは公開されています
  • 彼らはパブリックデフォルトコンストラクタを持っています

私のNHibernateのバージョンは3.3です。

私の最後の考えは、製品に別のマッピングを使用する必要があるということですが、なぜ CustomerProxy (およびその他) で機能するのでしょうか? 私の意見では、Customer と BaseObject は Product と Product1 と同じ関係にあります。

それは継承マッピングでしょうか?私が見ていない別の問題はありますか?

更新:オブジェクトを呼び出す前にオブジェクトのプロキシを解除しようとしましたRefresh(obj)が、メソッドは引き続き Product1Proxy を返します。それから私は試しmyObject is INHibernateProxyましたが、それは常にfalseと評価されます。NHibernate が自身のプロキシを認識しないのはなぜですか?

update2:タイプ Product1Proxy の myObject は、その baseobject が Product1 ではなく Product であると述べていることに気付きまし。私は完全に間違っていますか、それともそうあるべきですか?

update3:

session.Refresh((NHibernate.Proxy.INHibernateProxy)product);

たとえば、これにより無効なキャスト例外が発生します (Product1Proxy を INHibernateProxy にキャストできませんでした)。

if (kitProduct is NHibernate.Proxy.INHibernateProxy) {
...
}

決して真実ではありません...

そして、これを呼び出すと

IList kitProductTemplates = ProductManager.Instance.LoadProductTemplates(checkBoxShowHidden.Checked);

Product1 のリスト (実際の Product1 が返され、プロキシは返されません) ですが、そのリストを foreach で反復処理すると、オブジェクトはプロキシになります。クエリは次のようになります。

public IList LoadAllTemplates(bool showHidden)
{
    IList loadedObjects = (IList)new ArrayList();
    try
    {
        ISession session = HibernateSessionManager.Instance.GetSession();
        ICriteria crit = session.CreateCriteria(typeof(Product1));
        crit.Add(Restrictions.Eq("IsTemplate", true));
        crit.SetResultTransformer(new DistinctRootEntityResultTransformer());
        crit.AddOrder(Order.Asc("Name"));
        crit.SetFetchMode("PickingList", FetchMode.Join);
        crit.SetFetchMode("SOP", FetchMode.Join);

        if (!showHidden) {

            crit.Add(Restrictions.Eq("IsHidden", false));
        }
        loadedObjects = crit.List();
    }
    catch (Exception ex)
    {
        throw (ex);
    }
    return loadedObjects;
}

(これは私が見つけたばかりです。そうでなければ、以前に追加していたでしょう)

update4:問題を再度絞り込むことができます。オブジェクトが最初にロードされたセッションの場合は発生しません。しかし、考えられるすべてのユースケースでそれを保証することはできません。

敬具、期待

4

1 に答える 1