2010-12-14 78 views
1

J'essaie d'écrire Generic Repository dans EF 4. Mais mes codes ne sont pas beaux. Parce que ExpressionEntities n'est pas GENERIC.Comment écrire un nom d'entité générique dans un constructeur dans EF4?

Je veux convertir ce code:

public class DataRepository<T> : IRepository<T> where T : class 
{ 
    private ExpressionsEntities _context; 
    public DataRepository() 
    { 
    } 

    public DataRepository(ExpressionsEntities context) 
    { 
     _context = context; 
    } 
} 

à ce qui suit:

public class DataRepository<T> : IRepository<T> where T : class 
{ 
    private GetGenericEntityCONTEXT _context; 

    public DataRepository() 
    { 
    } 

    public DataRepository(GetGenericEntityCONTEXT context) 
    { 
     _context = context; 
    } 
} 

parce ExpressionsEntities non globales mes entités: ExpressionsEntities1, ExpressionsEntities 2, 3 ExpressionsEntities ETX ... Je dois écrire obtenir prendre l'entité par exemple:

public class DataRepository<T> : IRepository<T> where T : class 
{ 
    private Entity _context; 
    public DataRepository() 
    { 
    } 

    public DataRepository(Entity context) 
    { 
     _context = context; 
    } 

    public class Main 
    { 
     main() 
     { 
      new DataRepository(ExpressionEntities) 
     } 
    } 
} 

Répondre

1

Pas 100% sûr w chapeau que votre demande - de ce que je peux comprendre, vous wan't un moyen de dynamiquement créer le jeu d'entités basé sur T.

Eh bien, c'est assez facile:

public class DataRepository<T> : IRepository<T> where T : class 
{ 
    private ObjectContext _ctx; 

    public DataRepository<T>(ObjectContext ctx) 
    { 
     this._ctx = ctx; 
    } 

    public IObjectSet<T> CurrentEntitySet<T>() 
    { 
     get 
     { 
      var entityName = _plularizer.Pluralize(typeof(T).Name); 
      string entitySetName = string.Format("{0}.{1}", EntityContainerName, entityName); 
      return _ctx.CreateObjectSet<T>(entitySetName); 
     } 
    } 
} 

Ensuite, votre spécifique Repository pourrait le faire (par exemple):

public class AppleRepository : DataRepository<Apple> 
{ 
    public AppleRepository(IObjectContext ctx) : base(ctx) {} 

    public ICollection<Apple> FindApples(Func<Apple,bool> predicate) 
    { 
     return CurrentEntitySet.Where(predicate).ToList(); 
    } 
} 

Et lorsque votre création de votre référentiel, passer à travers le contexte de l'objet - de préférence par DI:

var repository = new AppleRepository(new ExpressionEntities()); // should be DI'ed 

Fondamentalement, nous faisons usage de pluralisation (le même code utilisé par Entity Framework pluraliser noms de jeu d'entités) et CreateObjectSet<T>.

Donc, si vous avez créé un DataRepository<Apple>, qui se traduirait par une entité nom de l'ensemble de pommes (qui doit correspondre à l'entité définie sur votre modèle), et nous créons un ensemble d'entités sur cette base.

La propriété EntityContainerName est ce qui se trouve sur votre EDMX - vous devez le faire passer par le ctor (via DI de préférence).

Est-ce que cela répond à votre question?

+0

Loo s'il vous plaît ci-dessus codes: Mes codes génériques mais ExpressionsEntities pas générique selon les codes ci-dessus je devrais écrire toutes les entités. – Penguen

+0

@Phsika - Qu'est-ce que "ExpressionEntities" - est-ce votre contexte de données? Je vais deviner et dire oui, et mettre à jour ma réponse. – RPM1984

+0

Et non, vous n'avez pas besoin d'un référentiel par entité. Vous devriez avoir un dépôt * par agrégat root *.Créez une interface pour chaque racine agrégée et injectez le DataRepository ou un référentiel spécifique (qui dérive du DataRepository et satisfait ainsi le contrat d'interface). Le point entier du référentiel générique est de réduire le nombre d'implémentations. – RPM1984

1

Je préfère obtenir le nom d'entité comme ceci.

EntityContainer container = context.MetadataWorkspace.GetEntityContainer(context.DefaultContainerName, DataSpace.CSpace);

EntitySetBase entitySet = container.BaseEntitySets.Where(item => item.ElementType.Name.Equals(typeof(T).Name)).FirstOrDefault();

var entityName = entitySet.Name

Ce traite certains cas, si vous avez quelques classes Pluralisé, et certaines classes non.