2011-07-22 11 views
5

Aquí está el problema.Cómo trae el Entity Framework Incluir método de extensión a un genérico IQueryable <TSource>

tengo una interfaz, y me para poner el método Include extensión, que pertenece a la biblioteca ADO.NET Entity Framework, a mi IRepository capa Dont wich es necesario que sabe de ADO.NET Entity Framework.

public interface IRepository<TEntity> 
{ 
    IQueryable<TEntity> Entities { get; } 

    TEntity GetById(long id); 
    TEntity Insert(TEntity entity); 
    void Update(TEntity entity); 
    void Delete(TEntity entity); 
    void Delete(long id); 
} 

Así que tienen el método de extensión:

public static class IncludeExtension 
{ 
    static IQueryable<TEntity> Include<TEntity>(this IQueryable<TEntity> query, 
     string path) 
    { 
     throw new NotImplementedException(); 
    } 
} 

Pero yo no sé cómo ponerlo en práctica en esta capa, y me enviarlo a mi ADO.NET Entity Framework (o lo que sea que implementarán el IRepository) para tratar.

Necesito la misma interfaz que con un método de extensión.

¿Alguna luz?

Respuesta

2

Esta pregunta es un poco viejo, pero aquí hay dos soluciones EF-independiente si usted o cualquier otra persona sigue buscando: basada en la reflexión

1. Solución

Esta solución es lo que el. NET Framework vuelve a si el IQueryable no se convierte en DbQuery o ObjectQuery. Omita estos lanzamientos (y la eficiencia que proporciona) y desacople la solución de Entity Framework.

public static class IncludeExtension 
{ 
    private static T QueryInclude<T>(T query, string path) 
    { 
     MethodInfo includeMethod = query.GetType().GetMethod("Include", new Type[] { typeof(string) }); 

     if ((includeMethod != null) && typeof(T).IsAssignableFrom(includeMethod.ReturnType)) 
     { 
      return (T)includeMethod.Invoke(query, new object[] { path }); 
     } 

     return query; 
    } 

    public static IQueryable<T> Include<T>(this IQueryable<T> query, string path) where T : class 
    { 
     return QueryInclude(query, path); 
    } 

    // Add other Include overloads. 
} 

2. Dyanmics solución basada

Aquí el método QueryInclude<T> utiliza el tipo de dynamic para evitar la reflexión.

public static class IncludeExtension 
{ 
    private static T QueryInclude<T>(T query, string path) 
    { 
     dynamic querytWithIncludeMethod = query as dynamic; 

     try 
     { 
      return (T)querytWithIncludeMethod.Include(path); 
     } 
     catch (RuntimeBinderException) 
     { 
      return query; 
     } 
    } 

    public static IQueryable<T> Include<T>(this IQueryable<T> query, string path) where T : class 
    { 
     return QueryInclude(query, path); 
    } 

    // Add other Include overloads. 
} 
3

Include es una abstracción con fugas y funciona solo con Entity framework. EF 4.1 already containsInclude sobre genéricos IQueryable pero internamente solo convierte los genéricos pasados ​​IQueryable en genéricos ObjectQuery o DbQuery y llama a sus Include.

Aquí hay un ejemplo de cómo ajustar ese include in repository (la implementación del repositorio depende de EF para que pueda usar Include proporcionado por EF directamente).

+0

Por lo tanto, simplemente no quiero depender de EF. Estoy tratando de evitar referencias en mi capa de cliente. – iuristona

0

En Entity Framework 5.0 ahora proporcionan un método de extensión a IQueryable para agregar la funcionalidad Incluir. Simplemente deberá agregar un uso de "System.Data.Entity" para resolver el método de extensión. Para documentación directa, vaya al here

Cuestiones relacionadas