IQueryable <T> с EntityObject, используя Generics & Interfaces (возможно?)

У меня есть поисковый репозиторий для EntityFramework 4.0 с использованием LinqKit со следующей функцией поиска:

public IQueryable<T> Search<T>(Expression<Func<T, bool>> predicate) 
    where T : EntityObject
{
    return _unitOfWork.ObjectSet<T>().AsExpandable().Where(predicate);
}

И еще один класс, который использует возвращаемое значение IQueryable для поднабора запроса способами, которые невозможны с помощью логических выражений LinqKit PredicateBuilder:

public IQueryable<T> SubsetByUser<T>(IQueryable<T> set, User user) 
    where T : EntityObject
{
    return set.Join(_searcher.Search<Metadatum>((o) => o.UserGUID == user.GUID),
                    arc => arc.GUID,
                    meta => meta.ElementGUID,
                    (arc, meta) => arc);
}

Проблема здесь в том, что «T» как EntityObject не определяет GUID, поэтому я не могу использовать это. Естественным ответом на это является фактическое определение метода SubsetByUser () для использования ограничения со свойством GUID:

public IQueryable<T> SubsetByUser<T>(IQueryable<T> set, User user) 
    where T : IHaveMetadata
{
    return set.Join(_searcher.Search<Metadatum>((o) => o.UserGUID == user.GUID),
                    arc => arc.GUID,
                    meta => meta.ElementGUID,
                    (arc, meta) => arc);
}

Но это не работает. Я использую LinqKit и метод Expandable () приводит к:

System.NotSupportedException: Unable to cast the type 'Oasis.DataModel.Arc' to
type 'Oasis.DataModel.Interfaces.IHaveMetadata'. LINQ to Entities only supports 
casting Entity Data Model primitive types

Мне нужен IQueryable для возвращения. Я могу сделать подделку, как это:

public IQueryable<T> SubsetByUser<T>(IQueryable<T> set, User user) 
    where T : EntityObject
{
    return set.AsEnumerable()
              .Join(_searcher.Search<Metadatum>((o) => o.UserGUID == user.GUID),
                    arc => arc.GUID,
                    meta => meta.ElementGUID,
                    (arc, meta) => arc)
              .AsQueryable();
}

Что, конечно, работает, но это также, конечно, безумное занятие. (Единственная причина, по которой я хочу IQueryable - не выполнять запрос до тех пор, пока мы не закончим.

Я даже попробовал это:

public IQueryable<T> SubsetByUser<T>(IQueryable<T> set, User user) 
    where T : EntityObject
{
    return set.Join(_searcher.Search<Metadatum>((o) => o.UserGUID == user.GUID),
                    arc => arc.GetType().GetProperty("GUID").GetValue(arc,null),
                    meta => meta.ElementGUID,
                    (arc, meta) => arc);
}

Который использует отражение, чтобы получить коллекцию Runs - обойти ошибку компилятора. Я думал, что это было довольно умно, но это приводит к исключению LINQ:

System.NotSupportedException: LINQ to Entities does not recognize the 
method 'System.Object GetValue(System.Object, System.Object[])' method, 
and this method cannot be translated into a store expression.

Я также мог бы попытаться изменить метод поиска:

public IQueryable<T> Search<T>(Expression<Func<T, bool>> predicate) 
    where T : IRunElement
{
    return _unitOfWork.ObjectSet<T>().AsExpandable().Where(predicate);
}

Но это, конечно, не скомпилируется, потому что IRunElement не является EntityObject, а ObjectSet ограничивает T как класс.

Последняя возможность - просто сделать все параметры и возвращаемые значения IEnumerable:

public IEnumerable<T> SubsetByUser<T>(IEnumerable<T> set, User user) 
    where T : EntityObject
{
    return set.Join(_searcher.Search<Metadatum>((o) => o.UserGUID == user.GUID),
                    arc => arc.GetType().GetProperty("GUID").GetValue(arc,null),
                    meta => meta.ElementGUID,
                    (arc, meta) => arc);
}

Что также работает, но, опять же, не позволяет нам откладывать создание экземпляров до конца.

Таким образом, кажется, что я мало что могу сделать, чтобы сделать эту работу, не создавая все экземпляры как IEnumerable, а затем возвращая его с помощью AsQueryable (). Есть ли какой-нибудь способ, которым я могу собрать это воедино, что мне не хватает?

Ответы на вопрос(1)

Ваш ответ на вопрос