IQueryable с Where, содержащим список, выдает «Не найдено сопоставления с реляционным типом для типа CLR« List <string>».» - PullRequest
0 голосов
/ 04 марта 2020

При использовании IBM.EntityFrameworkCore и IBM.Data.DB2.Core каждый раз выдается сообщение об ошибке, когда у меня есть Where оператор, содержащий список, для которого выполняется какая-то проверка.

выдается ошибка, когда IQueryable материализуется, т.е. преобразуется в список с использованием ToList().

. Невозможно найти сопоставление с реляционным типом для типа CLR «Список».

private IQueryable<CollectionActivityInOverview> FilterActivitiesForAdvisor(IQueryable<CollectionActivityInOverview> activitiesList, List<string> advisorCodes)
{
    List<AdvisorCustomerInfo>advisorInformation = GetAdvisorCustomers(advisorCodes).Result;
    var advisorCustomers = advisorInformation.SelectMany(a => a.Customers)
        .Distinct()
        .ToList();

    // This is the problematic spot
    activitiesList = activitiesList.Where(a => advisorCustomers.Any(ac => ac == a.CustomerId));

    return activitiesList;
}

.

public class AdvisorCustomerInfo
{
    public string AdvisorCode { get; set; }

    public List<string> Customers { get; set; }
}

В чем может быть ошибка, поскольку AFAIK, условия, использующие списки, должны поддерживаться не только Linq to Entities, но и Linq to SQL.

Возможно ли, что библиотека DB2 Entity Framework не поддерживает, т.е. не переводит такие условия в SQL?

Может кто-нибудь подтвердить это?

Мое основное требование - поддерживать IQueryable для выполнения запроса к базе данных. Можно ли переписать запрос, используя что-то еще?

1 Ответ

0 голосов
/ 22 марта 2020

Это правда, что DB2 EF Core Library (на данный момент) не поддерживает использование .Any() или .Contains(). Однако возможно «переопределить» это поведение, написав пользовательское выражение, которое имитирует SQL WHERE функцию с несколькими условиями в запросе.

По сути, вы передаете список, который хотите повторить, и вы добавьте каждый элемент списка в тело выражения, используя Expression.OrElse(). В конце вы возвращаете выражение, используя Expression.Call().

...