Repository générique avec EF 4.1 quel est le point

En approfondissant mes connaissances sur les interfaces DbContext, DbSet et associées, je me demande pourquoi vous devriez implémenter un référentiel “générique” distinct autour de ces implémentations?

Il semble que DbContext et IDbSet fassent tout ce dont vous avez besoin et incluent “Unit Of Work” dans DbContext.

Est-ce que je manque quelque chose ici ou semble-t-il que les gens aiment append une autre couche de dépendance sans aucune raison.

    Vous avez réellement raison. DbContext est une implémentation du modèle d’unité de travail et IDbSet est une implémentation du modèle de référentiel.

    Les référentiels sont actuellement très populaires et surutilisés. Tout le monde les utilise simplement parce qu’il existe des dizaines d’articles sur la création d’un référentiel pour le framework d’entités, mais personne ne décrit réellement les défis liés à cette décision.

    Les principales raisons d’utiliser le référentiel sont généralement les suivantes:

    • Masquer EF de la couche supérieure
    • Rendre le code plus facile à tester

    La première raison est une sorte de pureté architectonique et une excellente idée que si vous faites en sorte que vos couches supérieures soient indépendantes de la EF, vous pourrez plus tard passer à une autre structure de persistance. Combien de fois avez-vous vu une telle chose dans le monde réel? Cette raison rend le travail avec EF beaucoup plus difficile car votre référentiel doit exposer un grand nombre de fonctionnalités supplémentaires qui enveloppent ce que EF permet par défaut.

    Dans le même temps, le code EF peut mieux organiser votre code et suivre la règle de séparation des préoccupations. Pour moi, cela peut être le seul avantage réel du référentiel et de l’unité de travail, mais vous devez comprendre que suivre cette règle avec EF rendra peut-être votre code plus facile à maintenir et plus lisible, mais vous devrez pour les petites applications, cela peut être une complexité inutile.

    La deuxième raison est partiellement correcte. Le gros inconvénient de EF est une architecture rigide qui peut difficilement être moquée, donc si vous voulez unifier la couche supérieure du test, vous devez envelopper EF pour permettre son implémentation. Mais cela a beaucoup d’autres conséquences que j’ai décrites ici .

    Je suis le blog d’Ayende . Si vous avez déjà utilisé NHibernate, vous connaissez probablement ses articles. Ce gars a récemment écrit plusieurs articles contre l’utilisation du repository avec NHibernate, mais NHibernate est beaucoup mieux modifiable.

    Je suis aux sockets avec les mêmes problèmes, et il est important de se moquer des tests unitaires des couches EF. Mais je suis tombé sur cet excellent article qui explique comment configurer le EF 4.1 DbContext pour qu’il soit modifiable en s’assurant que votre DbContext dérivé implémente une interface générique et expose IDbSet plutôt que DbSet. Puisque j’utilise une approche Database First, car notre firebase database existe déjà, j’ai simplement modifié les modèles T4 utilisés pour générer mon DbContext dérivé afin de le générer pour renvoyer les interfaces IDbSet, ainsi que dériver de mon interface générique. De cette manière, tout peut être facilement moqué et vous n’avez pas besoin d’implémenter votre propre modèle d’unité de travail ou de référentiel. Il suffit d’écrire votre code de service pour consumr votre interface générique, et lorsque vous le testez, il suffit de simuler l’interface générique avec des données de test spécifiques et vous êtes prêt à partir.

    http://refactorthis.wordpress.com/2011/05/31/mock-faking-dbcontext-in-entity-framework-4-1-with-a-generic-repository/

    Une des raisons de la création du référentiel est que vous pouvez masquer l’implémentation de DBSet et DbContext si vous décidez de passer d’EntityFramework à autre chose ou vice versa.

    Par exemple, j’utilisais NHibernate et j’ai intégré tous les appels à ce cadre dans mes classes de référentiel. Ils renvoient IEnumerable pour que leurs get soient “génériques” et mes référentiels ont les opérations CRUD standard (update, delete, etc.). Je suis depuis longtemps passé chez Entity Framework. Ce faisant, je n’ai pas eu besoin de changer quoi que ce soit dans mes classes ViewModel ou au-delà car elles indiquaient mon référentiel – je n’avais qu’à changer l’intérieur de mon référentiel. Cela a rendu la vie beaucoup plus facile lors de la migration.

    (J’utilisais NHibernate parce que nous nous connections aux ISeries et, à l’époque, il n’y avait pas d’implémentations affectives coûteuses utilisant EF avec ISeries. Le seul disponible était de payer 12 000 $ à IBM pour leur DB2Connect)