2010-05-06 18 views
15

Estoy tratando de aprovechar NH para mapear a un modelo de datos que es una interpretación libre del modelo de datos EAV/CR.Uso de NHibernate con un modelo de datos EAV

Tengo la mayor parte trabajando, pero estoy luchando con el mapeo de la colección Entity.Attributes.

Estas son las tablas en cuestión:

-------------------- 
| Entities   | 
-------------------- 
| EntityId PK  |-| 
| EntityType  | | 
-------------------- | 
     ------------- 
     | 
     V 
-------------------- 
| EntityAttributes | ------------------ --------------------------- 
-------------------- | Attributes  | | StringAttributes  | 
| EntityId PK,FK | ------------------ --------------------------- 
| AttributeId FK | -> | AttributeId PK | -> | StringAttributeId PK,FK | 
| AttributeValue | | AttributeType | | AttributeName   | 
-------------------- ------------------ --------------------------- 

La columna AttributeValue se implementa como una columna sql_variant y yo he implementado un NHibernate.UserTypes.IUserType por ello.

Puedo crear una entidad EntityAttribute y persistirla directamente para que funcione la parte de la jerarquía.

No estoy seguro de cómo asignar la colección EntityAttributes a la entidad Entity.

Nota de la mesa EntityAttributes podría (y lo hace) contiene varias filas para una combinación dada EntityId/AttributeId:

EntityId AttributeId AttributeValue 
-------- ----------- -------------- 
1  1   Blue 
1  1   Green 

StringAttributes fila tiene este aspecto para este ejemplo:

StringAttributeId AttributeName 
----------------- -------------- 
1     FavoriteColor 

¿Cómo puedo efectivamente mapeo este modelo de datos a mi dominio Entity de tal manera que Entity.Attributes ("FavoriteColors") devuelva una colección de colores favoritos? ¿Mecanografió como System.String?

+0

¿Está utilizando fluidez? –

+0

Si planea encontrar entidades por valor de atributo, no estoy seguro de si sql_variant funciona correctamente. Deberías probar esto. –

Respuesta

1

aquí va

class Entity 
{ 
    public virtual int Id { get; set; } 

    internal protected virtual ICollection<EntityAttribute> AttributesInternal { get; set; } 

    public IEnumerable<T> Attributes<T>(string attributeName) 
    { 
     return AttributesInternal 
      .Where(x => x.Attribute.Name == attributeName) 
      .Select(x => x.Value) 
      .Cast<T>(); 
    } 
} 

class EntityAttribute 
{ 
    public virtual Attribute Attribute { get; set; } 

    public virtual object Value { get; set; } 
} 

class EntityMap : ClassMap<Entity> 
{ 
    public EntityMap() 
    { 
     HasMany(e => e.AttributesInternal) 
      .Table("EntityAttributes") 
      .KeyColumn("EntityId") 
      // EntityAttribute cant be an Entity because there is no real Primary Key 
      // (EntityId, [AttributeId] is not unique) 
      .Component(c => 
      { 
       c.References(ea => ea.Attribute, "AttributeId").Not.LazyLoad(); 
       c.Map(ea => ea.Value, "AttributeValue").CustomType<VariantUserType>(); 
      }); 
    } 
} 
Cuestiones relacionadas