1

Using the following classes..

public class Trait
{
    public virtual int Id { get; set; }
    public virtual string Name { get; set; }
}
public class Sheet
{
    public virtual int Id { get; set; }
    public virtual IDictionary<Trait, int> Influences { get; set; }
}

I have tried to map them using Fluent nHibernate, as such.

public class TraitMap : ClassMap<Trait>
{
    public TraitMap()
    {
        Id(x => x.Id);
        Map(x => x.Name);
        Table("Traits");
    }
}
public class SheetMap : ClassMap<Sheet>
{
    public SheetMap()
    {
        Id(x => x.Id);

        HasManyToMany<Trait>(x => x.Influences)
            .Schema("Sheets")
            .Table("Influences")
            .ParentKeyColumn("Trait")
            .ChildKeyColumn("Sheet")
            .AsMap<int>("Rating")
            .Cascade.All();

        Table("Sheets");
    }
}

This does not work. I get the exception.

Exception occurred getter of Trait.Id

Now, if I change the Dictionary up to look like this..

public class Sheet
{
    public virtual int Id { get; set; }
    public virtual IDictionary<int, Trait> Influences { get; set; }
}

Basically making the int the Key, and the Trait the value (not what I want), it does work. Can anyone explain this, and how I can more appropriately reproduce what I am trying to do?

I think the reasoning is because when I specify HasManyToMany<Trait> I am specifying the Value element of the collection. However this is not my intention.

I want to look things up by the Name of the Key, not the Name of the Value. While I realize this is technically an 'acceptable' solution, it kind of goes against the Dictionary convention. I'd prefer to take a more convention over solution approach, if at all possible - and I'd like to better understand what is actually going on under the hood.

Ciel
  • 17,312
  • 21
  • 104
  • 199

1 Answers1

3

What you want is what <composite-index> mapping in hbm would give you. I believe that instead of AsMap, you'd want AsEntityMap. However, look at this thread which talks about a rewrite (in august) of the fluent mapping for Maps that makes all of the above obsolete.

EDIT : For AsEntityMap, and other options, take a look at this SO question and answer

  HasMany<Trait>(x => x.Influences)
    .KeyColumn("key column name")
    .AsEntityMap("referenced column name")
    .Entity("dict value", v=> v.Type<int>());

Also, you say you're on the latest version - the latest release is 1.1, but trunk is 2.0, and is very different, and much further along. If you're not on 2.0+, you wouldn't see the methods posted in most of the help threads like the one linked above.

Community
  • 1
  • 1
Philip Rieck
  • 32,368
  • 11
  • 87
  • 99
  • I have read that thread, and unfortunately it did not make much sense to me. I actually found it before I even posted this question. Furthermore, I have the latest build of fluent nhibernate, and I did not find the .Index method from HasMany(). – Ciel Oct 13 '10 at 15:36
  • Could I bother you to cite an example of how I might use AsEntityMap to fix this? I am still quite confused. – Ciel Oct 13 '10 at 15:42
  • @Stacey Added some edits, hope that helps 1.1 and 2.0 are so different that it's hard to find help (the experts are on 2.0, but the released ver is 1.1) - and hard to remove. – Philip Rieck Oct 13 '10 at 15:54
  • I'm not sure what you mean by 'Trunk'. I don't use github, and I'm having a very hard time following how to download the appropriate files. – Ciel Oct 13 '10 at 16:13
  • Have you downloaded the latest build or 1.1? If the latest build is significantly different from 1.1 when it comes to Dictionary support. – James Gregory Oct 13 '10 at 16:28
  • I go to http://github.com/jagregory/fluent-nhibernate and click on the "Downloads" button. Then I click "Download Zip", it says "Branch Master". I get a file named jagregory-fluent-nhibernate-release-1.1-27-ga52c03d.zip – Ciel Oct 13 '10 at 16:32