2009-03-23 8 views
31

Fluent NHibernateに切り替えただけで、問題が発生し、その情報が見つかりませんでした。Fluent NHibernate、インターフェイスで動作する

ここケースです:

public class Field : DomainObject, IField 
{ 
    public Field() 
    { 
    } 

    public virtual string Name { get; set; } 
    public virtual string ContactPerson { get; set; } 
    public virtual bool Private { get; set; } 
    public virtual IAddress Address { get; set; } 
} 

IAddressは、住所

public class Address : DomainObject, IAddress 
{ 
    public Address() 
    { 
    } 

    public virtual string City { get; set; } 
    public virtual string Country { get; set; } 
    public virtual string PostalCode { get; set; } 
    public virtual string StreetAddress { get; set; } 
} 

ここでは、両方のクラスのための私のマッピングファイル

ADDRESS

public class AddressMap : ClassMap<Address> 
{ 
    public AddressMap() 
    { 
     WithTable("Addresses"); 
     Id(x => x.Id, "Id").Access.AsCamelCaseField(Prefix.Underscore).GeneratedBy.Guid(); 
     Map(x => x.City, "City"); 
     Map(x => x.Country, "Country"); 
     Map(x => x.PostalCode, "PostalCode"); 
     Map(x => x.StreetAddress, "StreetAddress"); 
    } 
} 
だというクラスによって実装されるインタフェースであり、

FIELD

public class FieldMap : ClassMap<Field> 
{ 
    public FieldMap() 
    { 
     WithTable("Fields"); 
     Id(x => x.Id, "Id").Access.AsCamelCaseField(Prefix.Underscore).GeneratedBy.Guid(); 
     Map(x => x.Name, "Name"); 
     Map(x => x.ContactPerson, "ContactPerson"); 
     Map(x => x.Private, "Private"); 
     References(x => x.Address, "AddressId").Cascade.Delete().Cascade.SaveUpdate(); 
    } 
} 

私は私のデータベースからフィールドオブジェクトをretriveしようとしたときに、私はIAddressがマップされていないと述べてNHibernateのエラーを取得します。 NHibernateにマッピングでAddressクラスを使用するよう指定する方法はありますか?

詳細情報が必要な場合は教えてください。あなたのFieldオブジェクトで

どうもありがとう、

チャールズ

+0

データベースでIAddress階層をどのようにモデリングしていますか?階層あたりのテーブル(すべてのタイプのアドレスを保持する1つのテーブル)またはconcrete-per-class? Fluentに切り替えたと言ったので、XMLマッピングの例を投稿することで、達成しようとしていることを判断するのに役立ちます。 –

+0

実際、私はADO.NET Entity FrameworkからFluent NHibernateでNhibernateに切り替えました。私のデータベースには、すべてのタイプのアドレスを保持するテーブルがあります。ところで、私はこれらのインターフェイスを削除することに決めました。私はそれが役に立たないことに気付きました。しかし、私はその質問がまだ有効だと思う。 おかげで、 チャールズ –

答えて

35

具体的なクラスの代わりにインターフェイスをプロパティとして使用する正当な理由があることがわかりました。

たとえば、FieldクラスがAddressクラスの別のプロジェクトにあり、FieldクラスのプロジェクトのAddressクラスのプロジェクトに依存していない場合などです。

このような状況に対処する他の方法もありますが、最も簡単な方法は、しばしば、NHibernateにIAddressに使用する具象クラスを伝えることです。

あなたは今、このように、流暢NHibernateはでこれを行うことができます。

References(x => x.Address, "AddressId") 
    .Class(typeof(Address); 

残念ながらあなたはhasManyのかHasManyToManyでこれを行うことはできません。私はこれがC#での良い共分散サポートの欠如のために可能であるかどうかは分かりません。

+26

**更新:**あなたは '参考

(X => x.Address).Column( "のAddressId")を使用することができます。あなたは 'hasManyの' と 'HasManyToMany' で同じことを行うことができます'ジェネリック型パラメータを追加します。 – Jay

+0

+1の更新、ちょうど私が探していたもの、多くのありがとう。 – 4imble

+0

ありがとう、まさに私が探していたもの... HasMany()にチェーンされた.CollectionType()が動作しようとしましたが、動作していないようです。 – calebt

5

は、あなたがタイプIAddressのオブジェクトを持っています。これは、任意の数の異なる実装によって実装することができる。あなたが求めているところでは、各実装には独自のマッピングがあり、これはNHibernateが処理するためにいくつもの困難(不可能なもの)を導入します。

簡単な例を実証するのに役立ちます。 2つのIAddressの実装Address1とAddress2があるとします。それらはそれぞれ独自のテーブルtblAddress1とtblAddress2に保存されます。 Fieldオブジェクトをロードしようとすると、NHibernateが知っていることは、IAddressを実装するものがあることです。どの実装が永続化されたのかわかりません。任意のフィールドの子オブジェクトを取得するために使用するマッピングをどのように知っていますか?

さらに複雑ですが、この例では、宣言したオブジェクトの正確なタイプのマッピングが必要な理由を示しています。

0

具体的なクラスを指定するのではなく、ドメインレイヤーからORMを完全に切り離し、データレイヤー全体を参照する場合は、EmptyInterceptorを実装して両者の間をマッピングできます。

私の答えはhereです。

関連する問題