title: Nibernate Fluent and interface based domain model
body: <p>Ok, this has been a rather frustrating experience :)  I am trying to work with an interface based domain model and I can get ALMOST everything working with the exception of the ability to actually save data</p>
  
  <p>Here is what I have so far.  </p>
  
  <pre><code>public interface IEntity {
       Guid Id {get;set;}
  }
  
  public interface IProduct : IEntity {
       string Name {get;set;}
       string SKU {get;set;}
       decimal MSRP {get;set;}
  }
  
  public class Product : IProduct {
       public virtual Guid Id {get;set;}
       public virtual string Name {get;set;}
       public virtual string SKU {get;set;}
       public virtual decimal MSRP {get;set;}
  }
  
  public interface IOrder : IEntity {
       DateTime CreatedOn {get;set;}
       IList&lt;IOrderLine&gt; Lines {get;set;}
  }
  
  public class Order : IOrder {
       public virtual Guid Id {get;set;}
       public virtual DateTime CreatedOn {get;set;}
       public virtual IList&lt;IOrderLine&gt; Lines {get;set;}
  }
  
  public interface IOrderLine : IEntity {
       IProduct Product {get;set;}
       int Qty {get;set;}
       decimal Price {get;set;}
  }
  
  public class OrderLine : IOrderLine {
       public virtual Guid Id {get;set;}
       public virtual IProduct Product {get;set;}
       public virtual int Qty {get;set;}
       public virtual decimal Price {get;set;}
  }
  
  public class ProductMap : ClassMap&lt;IProduct&gt;
  {
       public ProductMap() {
           Id(x =&gt; x.Id);
  
           Map(x =&gt; x.Name);
           Map(x =&gt; x.SKU);
           Map(x =&gt; x.MSRP);
       }
  }
  
  public class OrderMap : ClassMap&lt;IOrder&gt;
  {
       public OrderMap() {
           Id(x =&gt; x.Id);
  
           Map(x =&gt; x.CreatedOn);
  
           HasMany(x =&gt; x.Lines)
              .KeyColumns.Add("Id");
       }
  }
  
  public class OrderLineMap : ClassMap&lt;IOrderLine&gt;
  {
       public OrderLineMap() {
           Id(x =&gt; x.Id);
  
           Map(x =&gt; x.Qty);
           Map(x =&gt; x.Price);
  
           References(x =&gt; x.Product)
               .PropertyRef(x =&gt; x.Id)
               .ForeignKey("productId");
       }
  }
  
  public static class NHibernateUtils
  {
      public static ISessionFactory CreateSessionFactory(IPersistenceConfigurer persistenceConfigurer)
      {           
          return Fluently.Configure()
              .Database(persistenceConfigurer)
              .Mappings(m =&gt;
              {
                  m.FluentMappings.Add&lt;ProductMap&gt;();
                  m.FluentMappings.Add&lt;OrderLineMap&gt;();
                  m.FluentMappings.Add&lt;OrderMap&gt;();
              })
              .ExposeConfiguration(c =&gt; new SchemaExport(c).Create(false, true))
              .BuildConfiguration()
              .BuildSessionFactory();
      }
  }
  </code></pre>
  
  <p>This works to create a valid scheme (I am testing sing Sqlite and can see the db created correctly).  The issue is when I try to save an actual entity.</p>
  
  <pre><code>var p = new Product() { Name = "Product Sample", SKU = "12345", MSRP = 1.0 };
  var sessionFactory = NHibernateUtils.CreateSessionFactory(...);
  
  using (var session = sesionFactory.OpenSession())
  {
      using (var transaction = session.BeginTransaction())
      {                   
          session.Save(p);
  
          transaction.Commit();
      }
  }
  </code></pre>
  
  <p>This fails with an error "no persister for Product"</p>
  
  <p>ok, I can see that -- so next I tried this</p>
  
  <pre><code>session.Save((IProduct)p);
  </code></pre>
  
  <p>and that gave me the error "no persister for IProduct"</p>
  
  <p>So what am I missing?</p>
  
  <p>Note: Here is a link to a gist that actually shows the issue in a running console app
  <a href="https://gist.github.com/ravensorb/14193136002adbb3ec2fac07c026f921" rel="nofollow noreferrer">https://gist.github.com/ravensorb/14193136002adbb3ec2fac07c026f921</a></p>