views:

566

answers:

2

I have different kinds of products. Now, the AppProduct has different kinds of quantities - multiply of value, list of values, etc...

   public class Product : Entity
   {
   }
   public class Quantity: Entity
   {
   }
   public class ListQuantity : Quantity
   {
      public virtual IList<int> Quantities { get; set; }
   }
   public class MultiplierQuantity : Quantity
   {
      public virtual int Multiplier { get; set; }
   }
   public class AppProduct : Product
   {
      public virtual Quantity Quantity { get; set; }
   }

The question is: is it possible to map with FNH or NH at all? Particularly, with auto mapping. To me it would be natural to map products in their own tables, but quantities would be part of AppProducts table... that is, discriminated.

I tried different Subclass, JoinedSubclass, etc. ways without luck, each with different NH exceptions. It works only when both hierarchies are mapped by default with joined subclass. However, automapper can't map IList[int] automatically. If I set IList[Product] (to test) everything works perfectly. If I try to keep IList[int] using this mapping:

   public class ListQuantityMap : IAutoMappingOverride<ListQuantity>
   {
      public void Override(AutoMap<ListQuantity> mapping)
      {
         mapping.HasMany(x => x.Quantities).AsElement("QuantitiesId");
      }
   }

if fails with System.Xml.Schema.XmlSchemaValidationException: The element 'class' in namespace 'urn:nhibernate-mapping-2.2' has invalid child element 'bag' in namespace 'urn:nhibernate-mapping-2.2'. List of possible elements expected: 'meta, subselect, cache, synchronize, comment, tuplizer, id, composite-id' in namespace 'urn:nhibernate-mapping-2.2'.

though the only difference in exported Orders.Core.Quantity.hbm.xml is one-to-many class type... i.e. NHibernate does not complain about bag in almost the same mapping.
(note: this is probably a bug that is fixed in recent FNH, issue #299).

Anyway, joined subclass is not the perfect solution here. I even think about doing just component in AppProduct and creating appropriate quantity object myself when property "QuantityType" is assigned... too weird, though. Or maybe switching to Linq2Sql will help? ;-)

+1  A: 

I am not sure what you are trying to accomplish. It looks like there might be some issues with your object model. For example, it looks like you have a class of quantity (as opposed to a standard property deriving from, perhaps, int). You might want to rethink this.

If you find you are running into problems with the AutoMapper, you can drop back and use standard (manual) mappings in conjunction with conventions.

I think the problem is most likely with your object model as opposed to a Fluent-NHibernate issue.

You can find the official fluent page on Subclass mappings at http://wiki.fluentnhibernate.org/Fluent_mapping.

Anthony Gatlin
It is not a quantity, it is "allowed quantities" which can be *n or 1,2,3,...n hence different strategy classes (and maybe I'd add third strategy later). These different classes help with GetNextAllowedQuanity()-like methods. I can have 1 component-like class and it will work... but in switch(quantityStrategy) style which is not very nice nor object-oriented.
queen3
Ok. I still don't quite understand. When you say "allowed quantities", do you mean some sort of quantity type? Is it like a unit of measure (eg. each, ounce, case, etc.)? It seems like what you might be saying is that for a particular type of product you want to be able to associate a list of allowable types for a specific quantity.
Anthony Gatlin
Well, actually my quantity types are expressed as classes in the code sample... For each product I need single quantity type, because this can be either multiplier or list of values. So, product1 will have field Multiplier = 5 and no values in table AllowedProductQuantities (ProductId, Value), and product2 will have Multiplier = null and few values in the table AllowedProductQuantities. Now, I'd like to see how to make Quantity a COMPONENT of Product, so that I have Product (Multiplier) field, and not ProductMultiplers table with (ProductId, Multiplier).
queen3
A: 

Different schema but I also have a need for something like this, although only two levels deep. That is, sub-class C inherits sub-class B inherits class A.

neogeo