Entity Framework Cache
Publié par Fabrice Michellonet sous le(s) label(s) le 5 septembre 2012Malgré la version 5 d'Entity Framework sortie il y a peu de temps, beaucoup déplorent l’absence d’un mécanisme de cache implémenté dans le Framework.
Pour ceux qui ont un peu creusé le sujet, il y a bien les "Tracing and Caching Provider Wrappers for Entity Framework" parus début 2011. Cependant, ce n’est pas la solution ultime ; à l’époque Code First n’existait pas ce qui rend cette librairie incompatible avec Code First.
Pour être tout à fait franc, le code des wrappers est disponible, je pense donc qu’en bidouillant un peu, ça doit être possible d’adapter le code pour Code First.
A l’occasion de la sortie d’EntityFramework.Patterns 0.7, je vous propose de voir ensemble comme utiliser les fonctionnalités de cache fournies par cette librairie.
Soit le contexte suivant :
public class EfContext : DbContext
{
public DbSet<User> Users { get; set; }
public EfContext()
{
Database.SetInitializer(new DropCreateDatabaseIfModelChanges<EfContext>());
}
}
Et l’entité User tel que :
public class User
{
public int Id { get; set; }
public string Name { get; set; }
public virtual ICollection<UserRole> UserRoles { get; set; }
}
On peut facilement utiliser le cache en mémoire (il est possible d’en utiliser d’autre) fournit par EntityFramework.Patterns pour mettre en cache une collection de User.
// On charge tous les users et on les stocke dans le cache.
using (EfContext ctx = new EfContext())
{
IEnumerable<User> usrs = ctx.Users.ToCache();
}
// autre code...
// Cette fois ci, on récupère les users à partir du cache.
using (EfContext ctx = new EfContext())
{
IEnumerable<User> usrs = ctx.Users.FromCache();
}
Simple non ?
Pour ceux qui préfèrent éviter l’accès direct au context d’Entity Framework et qui isolent leur accès à la base dans des repository, EntityFramework.Patterns vous facilitera la tâche également.
Il vous suffit de wrapper votre Repository
using (EfContext ctx = new EfContext())
{
DbContextAdapter adpt = new DbContextAdapter(ctx);
IRepository<User> repo =
new CacheableRepository<User>(
new Repository<User>(adpt)
);
// On charge tous les utilisateurs.
// Par defaut le CacheableRepository va mettre en cache le resultset
// en provenance de la base et le réutilisera le cas échéant plus tard.
IEnumerable<User> usrs = repo.GetAll();
// autre code.
// Cette fois-ci, les users proviennent du cache. Il n'y a pas d'accès en base.
usrs = repo.GetAll();
}
Comme vous le voyez le CacheableRepository fait appel au cache pour vous ; et vous permet de ne pas avoir à gérer la suppression d’éléments dans le cache lorsque les éléments ont étés modifiés/supprimés/insérés etc…
Je reviendrais ultérieurement dans un prochain post sur les mécanismes avancés du cache proposés par EntityFramework.Patterns.
0 commentaires:
Enregistrer un commentaire