2012-06-19 14 views
5

acabo de ver realización de GenericRepository:GenericRepository y EF. ¿Esta bien?

namespace ContosoUniversity.DAL 
{ 
    public class GenericRepository<TEntity> where TEntity : class 
    { 
     internal SchoolContext context; 
     internal DbSet<TEntity> dbSet; 

     public GenericRepository(SchoolContext context) 
     { 
      this.context = context; 
      this.dbSet = context.Set<TEntity>(); 
     } 

     public virtual IEnumerable<TEntity> Get(
      Expression<Func<TEntity, bool>> filter = null, 
      Func<IQueryable<TEntity>, IOrderedQueryable<TEntity>> orderBy = null, 
      string includeProperties = "") 
     { 
      IQueryable<TEntity> query = dbSet; 

      if (filter != null) 
      { 
       query = query.Where(filter); 
      } 

      foreach (var includeProperty in includeProperties.Split 
       (new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries)) 
      { 
       query = query.Include(includeProperty); 
      } 

      if (orderBy != null) 
      { 
       return orderBy(query).ToList(); 
      } 
      else 
      { 
       return query.ToList(); 
      } 
     } 

     public virtual TEntity GetByID(object id) 
     { 
      return dbSet.Find(id); 
     } 

     public virtual void Insert(TEntity entity) 
     { 
      dbSet.Add(entity); 
     } 

     public virtual void Delete(object id) 
     { 
      TEntity entityToDelete = dbSet.Find(id); 
      Delete(entityToDelete); 
     } 

     public virtual void Delete(TEntity entityToDelete) 
     { 
      if (context.Entry(entityToDelete).State == EntityState.Detached) 
      { 
       dbSet.Attach(entityToDelete); 
      } 
      dbSet.Remove(entityToDelete); 
     } 

     public virtual void Update(TEntity entityToUpdate) 
     { 
      dbSet.Attach(entityToUpdate); 
      context.Entry(entityToUpdate).State = EntityState.Modified; 
     } 
    } 
} 

aquí: http://www.asp.net/mvc/tutorials/getting-started-with-ef-using-mvc/implementing-the-repository-and-unit-of-work-patterns-in-an-asp-net-mvc-application y yo creo que es muy bonito, pero me gustaría hacerle una pregunta. ¿Cuáles son los pros y los contras de este enfoque con la realización separada (cada repositorio de entidad en clase separada)?

Respuesta

1

Este es un gusto más personal que cualquier otra cosa. Personalmente, no me gusta el término Repositorio porque es demasiado genérico y el significado/propósito del repositorio se ha perdido. Encuentro que los repositorios a menudo son genéricos y repetitivos, como si cada entidad necesitara su propio repositorio. y luego el repositorio obtiene demasiados métodos de consulta. muy pronto terminas con una clase divina para el acceso a los datos. Esta ha sido mi experiencia.

con el repositorio genérico puede usar la herencia a subclase para entidades específicas para consultas de encendido y apagado. Prefiero la composición por encima de la herencia, por lo que es otra razón por la que evito el término/uso de repos.

En su lugar, me gusta pensar en el acceso a los datos como consulta (leer) & comando (escribir) objetos. donde cada objeto tiene 1 método para recuperar una proyección específica (consulta) de los datos o modificar los datos persistentes (comando).

al final, siempre y cuando & su equipo entienda la arquitectura y el código es mantenible, tiene una solución sólida. No es realmente bueno o malo.

+0

Thx por su respuesta –

1

Incluso si decide que necesita tener clases concretas Repository para cada entidad, aún tiene sentido absoluto, como mínimo, utilizar un repositorio genérico como base para no duplicar el código, y puede probar la funcionalidad común en un lugar.

De manera realista, esta práctica no tiene inconvenientes. Si necesita descubrir cómo uno de los métodos funciona para una entidad específica, simplemente anule, solucione y asegúrese de que esté cubierto en una prueba unitaria.

+0

Entonces, ¿es una 'bala de plata' para la realización del patrón de repositorio? –

+0

"Silver bullet" es una palabra cargada ... no, no puedo decir que sea eso; El argumento de que puede convertirse en una abstracción con goteras es beneficioso, ya que, para completar una tarea de manera eficiente, es posible que necesite utilizar funcionalidades específicas de ORM, y exponer esa funcionalidad genéricamente puede ser una pesadilla. Sin embargo, el 95% de las veces, no lo necesito, y como @Steven dice en su respuesta, son (en mi humilde opinión) demasiado útiles para ser ignorados. Vea mi respuesta aquí para más detalles, y cómo manejo el 5% de las situaciones que son complicadas con repositorios genéricos http://stackoverflow.com/a/10925510/64750 – HackedByChinese

+0

Gracias por su respuesta y enlace –

1

Existen varias opiniones sobre el uso de decoradores genéricos. Básicamente hay dos campamentos. El primer campo encuentra que el repositorio genérico es una abstracción con goteras, lo que significa que a menudo no estás realmente abstrayendo el origen de datos con él. Por lo tanto, no debe utilizarse en absoluto. Lea por ejemplo this answer.

Estoy en el segundo campamento. Sé que es una abstracción con goteras, pero un repositorio genérico (especialmente con soporte de IQuerable), solo conduce a un código demasiado expresivo y comprobable, que debe ignorarse. He escrito an article about generic repositories. Es un enfoque alternativo para acercarse a sus puntos de enlace. Le da un enfoque diferente a los repositorios genéricos, con el foco en la facilidad de mantenimiento y la capacidad de prueba. Lo podrías encontrar útil.

+0

¡Muchas gracias por tu respuesta y artículo! –

Cuestiones relacionadas