4

すでにそこにオンポイントの答えがあるが、私はそれを見つけられなかった場合はお詫び申し上げます。NH3を使用していて、クラスが特定のインターフェイスを実装しているエンティティにSetを追加したいというユースケースがあります。構成ビルダークラスがあるので、セッションファクトリを作成する前にこれらの変更を行うことができます。

この縮小された例を考えると:

public class Person : IHasExtraItems
{
    public Person()
    {
        this.ExtraItems = new HashSet<ExtraItem>();
    }
    public virtual Guid Id { get; set; }
    public virtual string Name { get; set; }
    public virtual DateTime Birthdate { get; set; }
    public virtual ICollection<ExtraItem> ExtraItems { get; protected set; }
}

public class ExtraItem
{
    public virtual Guid Id { get; set; }
}

そして、このマッピング例:

  <class name="Person">
    <id name="Id">
      <generator class="guid"/>
    </id>
    <property name="Name"/>
    <property name="Birthdate"/>
    <set name="Extra" table="PersonExtraItems" cascade="all">
      <key column="PersonId"/>
      <many-to-many column="ExtraItemId" class="ExtraItem" unique="true" />
    </set>
  </class>

この機能を多くのクラスに透過的に適用できるようにしたいので(インターフェースを実装するだけで)、マッピングに「ExtraItem」を入れたくありません。代わりに、実行時に追加したいと思います。したがって、xmlマッピングからプロパティを削除した場合、実行時にこれを追加するにはどうすればよいですか?

私が行おうとしている変更の種類を正確に説明しているものがあります:http: //ayende.com/Blog/archive/2008/05/01/Dynamic-Mapping-with-NHibernate.aspx

しかし、多対多のセットをマッピングするわけではなく、私の弱い脳は、nhibernateが効果を作成するために使用するメモリ内マッピング表現を解読できませんでした。これは、デバッガーに表示されるプロパティを一致させようとすることに基づいて、私がこれまでに最も近いものです。

foreach (var cls in cfg.ClassMappings)
{
    if (typeof(IHasExtraItems).IsAssignableFrom(cls.MappedClass))
    {
        NHibernate.Mapping.Property property = new NHibernate.Mapping.Property();
        NHibernate.Mapping.Set value = new NHibernate.Mapping.Set(cls);
        value.Role = cls.EntityName + ".ExtraItems";
        value.IsGeneric = true;
        var table = new Table();
        table.Name = cls.MappedClass.Name + "ExtraItems";
        value.CollectionTable = table;
        value.GenericArguments = new Type[] { typeof(ExtraItem) };
        value.IsOptimisticLocked = true;
        value.IsLazy = true;
        mappings.AddCollection(value);
        property.Value = value;

        property.Name = "ExtraItems";
        property.PersistentClass = cls;
        property.Cascade = "all";
        cls.AddProperty(property);
    }
}

テストでは、キーがnullであるため、これによりランタイムエラーが発生しますが、XMLマップバージョンは機能し、変更を加えた時点ではほぼ同じように見えます。

ボーナスポイント:結合されたテーブルが必要なため、特に多対多が必要です。これにより、パフォーマンスのために、真の外部キーを使用してエンティティを拡張データにマップできます。ExtraItemsは実際には真のエンティティではなく値型である必要がありますが、XMLであっても、それをマップする方法を理解できませんでした。

ボーナスポイント、パート2: confORMでこれを行うことはできますか?既存のすべてのマッピングをconfORMに切り替えたくありません。また、confORMを従来のXMLマッピングと混合する例を見つけることができませんでした。既存のマッピングを変更してもかまいません。Fluentは別のオプションですが、私はNH3を使用しており、Fluentはまだそれをサポートしていないと思います。

前もって感謝します!

編集私の問題は、セットの要素を定義していないことだとかなり確信しています。ただし、セットの要素を適切に定義する方法がわかりません。

4

1 に答える 1

1

NH3 用の流暢なビルドがあるので、それを使用できます (私は使用しています)。流暢を使用している場合は、規則を使用してこれを非常に簡単に行うことができます。ボーナスポイントのセクションでそれについて言及しているので、もう一度見てみる必要がありますか?

于 2011-03-02T21:02:52.260 に答える