0

A bit new at the Repository Pattern. Trying to build a generic repository that will also handle state changes to derived entities. What I've done so far is create a custom attribute to flag the property as one which needs to be upserted.

Attribute:

public class DerivedObjectAttribute : Attribute
{
    public enum EntityType
    {
        REFERENCE,
        OBJECT
    }

    public EntityType DerivedType { get; set; }
}

I define this attribute for any property on which I want to cascade state changes.

Sample Entity:

public class FightingCharacter : BaseEntity 
{
    public Costume costume { get; set; }

    [DerivedObject(DerivedType=DerivedObjectAttribute.EntityType.REFERENCE)]
    public SpecialFinish specialFinish { get; set; }

    [DerivedObject(DerivedType = DerivedObjectAttribute.EntityType.REFERENCE)]
    public List<MoveList> moveList { get; set; }
}

So for this class, the costume property would not need to cascade, but the specialFinish and moveList properties should.

Then in my repository:

public class DataRepository<T> : IRepository<T> where T : BaseEntity {
    private void TryDerivedUpsert(T entity)
    {
        Type type = entity.GetType();
        PropertyInfo[] piList = type.GetProperties();
        foreach (PropertyInfo pi in piList)
        {
            foreach (DerivedObjectAttribute attr in pi.GetCustomAttributes(typeof(DerivedObjectAttribute), false))
            {
                // What to do here?
            }
        }
    }
}

In the innermost loop, I'm able to pinpoint DerivedObjectAttributes without any problem. The question is: how do I obtain the Type and Value of the object, then upsert it? In other words: if property pi is flagged to cascade changes, create a repo cast to the appropriate Entity, and Upsert it. E.G.:

DataRepository<EntityType> repo = new DataRepository<EntityType> ();
repo.Upsert(property as EntityType);

Does that make sense? Or am I going about generic repo entirely the wrong way? If it does make sense (I'll be surprised), how to do it? (The examples listed here are just examples, BTW. I'm still architecting and have no EF classes at all yet.)

4

1 回答 1

0

您可以使用 获取值pi.GetValue(entity, null),并为属性类型(来自 pi)创建通用存储库 ( Activate.CreateInstance),但您必须进行大量反思。

在这种情况下,您应该考虑放弃经典的通用存储库思想(每种类型的存储库),并使用DbContext可以处理所有类型的扩展库之类的东西。

如果您有断开连接的场景 (WCF),主要问题将是 EF 本身,因为您必须将所有更改复制到服务器端的嵌套列表并手动更改 EntityState。

于 2012-07-03T06:56:22.620 回答