Domanda

I am trying to implement an interface from a another project and persist that to a data base using fluent nhibernate. I have figured out how to persist a single instance of the interface but can not figure out how to do the entire list.

My class definitions are as follows:

public interface IRunnable { int Velocity { get; set; } int GetSpeed(); }

public class Person : IRunnable
{
    public virtual int Id { get; set; }
    public virtual string Name { get; set; }
    //public virtual IList<Car> Cars { get; set; }

    public Person()
    {
        //this.Cars = new List<Car>();
    }

    public virtual int GetSpeed()
    {
        return -1;
    }

    public virtual int Velocity { get; set; }
}

public class Person1 : IRunnable
{
    public virtual int Id { get; set; }
    public virtual int Age { get; set; }
    public virtual int Velocity { get; set; }

    public virtual int GetSpeed()
    {
        return 0;
    }
}

public class Car
{
    public virtual int Id { get; set; }
    public virtual IRunnable Runnable { get; set; }

    public virtual IList<IRunnable> Runnables { get; set; }

    public Car()
    {
        Runnables = new List<IRunnable>();
    }
}

Mapping definitions are

 public class Person1Map : ClassMap<Person1>
{
    public Person1Map()
    {
        Id(x => x.Id);
        Map(x => x.Age);
        Map(x => x.Velocity);
    }
}

public class PersonMap : ClassMap<Person>
{
    public PersonMap()
    {
        Id(x => x.Id);
        Map(x => x.Name);
        Map(x => x.Velocity);
        //HasMany(x => x.Cars).Cascade.All();
    }
}

public class CarMap : ClassMap<Car>
{
    public CarMap()
    {
        Id(x => x.Id);

        ReferencesAny<IRunnable>(x => x.Runnable)
            .IdentityType<int>()
            .EntityTypeColumn("RunnableType")
            .EntityIdentifierColumn("RunnableId")
            .AddMetaValue<Person>("P")
            .AddMetaValue<Person1>("P1")
            .Cascade.All();

        HasMany(x => x.Runnables)
            .KeyColumn("RunnableId")
            .Cascade
            .All();

    }
}

The references Any works great for a single instance of the interface how can I use something like this when I have entire list of the interface?

Thanks!

È stato utile?

Soluzione

The answer for fluent NHibernate is here: https://github.com/jagregory/fluent-nhibernate/issues/56, an extract:

Many-to-any support

We still don't support many-to-any

How the many-to-any is working could be in detailed observed here: Ayende, NHibernate mapping, many-to-any

But the most important information could be found here: 6.10. Heterogeneous Associations

The <many-to-any> and <index-many-to-any> elements provide for true heterogeneous associations. These mapping elements work in the same way as the element - and should also be used rarely, if ever.

NOTE: Please, try to re-think your model. My experience is that the simplification from any but short perspective wins. Other words, If we have a class like Tag, which could be referenced almost anywhere... usually we do not introduce IList<A> A, IList<B> B .. into Tag itself. But we still can find the Tags related to A... with some querying

Altri suggerimenti

HasMany with interfaces is not that easy, or lets say it has some limitations.

It depends a little bit on your mapping strategy how your inheritance works. Have a look here for documentation.

And you can find a good post already on SO about it here...

Basically you might have to add a class map for your interface and create subclass mappings for your implementations. This would be table per concrete class mapping which should work fine.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top