2012-06-19 18 views
5

Właśnie widziałem realizację od GenericRepository:GenericRepository and EF. Czy to jest dobre?

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; 
     } 
    } 
} 

tutaj: 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 i myślę, że to jest naprawdę ładne, ale chciałbym zadać panu pytanie. jakie są plusy i minusy tego podejścia z odrębną realizacją (repozytorium każdej jednostki w osobnej klasie)?

Odpowiedz

1

To bardziej osobisty gust niż cokolwiek innego. Osobiście nie podoba mi się termin Repozytorium, ponieważ jest zbyt ogólny i utracono znaczenie/cel repozytorium. Uważam, że repozytoria są często ogólne i powtarzalne, tak jakby każdy podmiot potrzebował własnego repozytorium. a następnie repozytorium pobiera zbyt wiele jednorazowych metod do odpytywania. niedługo skończysz z klasą boga dla dostępu do danych. To było moje doświadczenie.

z ogólnym repozytorium można używać dziedziczenia podklasy do określonych podmiotów dla zapytań typu on-off. Wolę kompozycję niż dziedziczenie, więc kolejny powód, dla którego unikam terminu/użycia repo.

zamiast tego lubię myśleć o dostępie do danych jako zapytanie (odczyt) & polecenie (zapis) obiektów. gdzie każdy obiekt ma 1 metodę pobrania określonej projekcji (zapytania) danych lub zmodyfikowania utrwalonych danych (polecenie).

W końcu tak długo, jak & Twój zespół rozumie architekturę, a kod można konserwować, masz solidne rozwiązanie. To nie jest dobre ani złe.

+0

Thx za odpowiedź –

1

Nawet jeśli zdecydujesz, że musisz mieć konkretne klasy Repository dla każdej jednostki, to w dalszym ciągu absolutnie sensowne jest używanie jako repozytorium podstawowego repozytorium, aby nie duplikować kodu, i przetestować wspólną funkcjonalność w jedno miejsce.

Realistycznie nie ma żadnych przeciwwag do tej praktyki. Jeśli chcesz kofuować działanie jednej z metod dla konkretnej jednostki, po prostu ją przesłonisz, napraw i upewnij się, że jest objęta testem jednostkowym.

+0

Czy jest to więc "srebrna kula" do realizacji repozytorium? –

+0

"Srebrna kula" to załadowane słowo ... nie, nie mogę powiedzieć, że to; Argument, że może stać się nieszczelną abstrakcją, polega na tym, że efektywne wykonywanie zadania może wymagać użycia funkcji specyficznej dla ORM, a ogólna ekspozycja może być koszmarem. Jednak w 95% przypadków nie potrzebuję tego, a ponieważ @Steven mówi w swojej odpowiedzi, są one (IMHO) zbyt użyteczne, aby je zignorować. Zobacz moją odpowiedź tutaj, aby uzyskać więcej szczegółów i jak sobie z tym poradzić 5% sytuacji, które są trudne z generycznymi repozytoriami http://stackoverflow.com/a/10925510/64750 – HackedByChinese

+0

Thx za odpowiedź i link –

1

Istnieje kilka opinii na temat korzystania z generycznych dekoratorów. Zasadniczo istnieją dwa obozy. Pierwszy obóz stwierdza, że ​​repozytorium generyczne jest nieszczelną abstrakcją, co oznacza, że ​​często nie wyodrębnia się źródła danych. Dlatego nie należy go w ogóle używać. Przeczytaj na przykład this answer.

Jestem w drugim obozie. Wiem, że jest to nieszczelna abstrakcja, ale ogólne repozytorium (szczególnie z obsługą IQuerable), prowadzi do zbyt ekspresywnego i testowalnego kodu, aby zostać zignorowanym. Napisałem an article about generic repositories. To alternatywne podejście do dodawania linków. Daje to inne podejście do repozytoriów ogólnych, ze szczególnym uwzględnieniem możliwości konserwacji i testowalności. Może się przydać.

+0

Dużo za odpowiedź i artykuł! –

Powiązane problemy