OData с использованием операции разворота $expand из-за оболочки

Я испытываю ту же проблему, что и адрес здесь:

Однако ответа мне недостаточно. Прежде всего, я не могу для жизни меня найти HierarchyNodeExpressionVisitor в OData 5.0.0 (не RC1) (или где-нибудь в этом отношении, попробовал поиск по сайту).

Второй, даже если я нашел, что возвращение IHttpActionResult недостаточно, мне нужно вернуть напечатанный PageResult<MyViewModel>

Заявленное оправдание для возврата IHttpActionResult означает "обрабатывать тот факт, что результат может быть не более IQueryable<MyEntity>". после использования оператора $expand.

Но для меня это не имеет смысла, потому что я думал, что оператор $expand используется для включения свойства навигации для объекта точно так же, как на стороне сервера Include(e => e.RelatedProperty). По крайней мере, в моем случае я включаю только свойство уже в Entity, поэтому мне не нужно беспокоиться об этом "потенциально являясь чем-то другим".

Однако при использовании $expand=Department я не могу Cast<>() присвоить тип объекта, потому что он не может отличить SelectAllAndExpand<MyEntity> до MyEntity.

Как я могу "развернуть" расширение обратно к исходной сущности, чтобы сделать проекцию?

public PageResult<DateSnippetWithDepartmentsViewModel> GetDatesWithDepartments(ODataQueryOptions<DateSnippet> options)
{
    IQueryable query = options.ApplyTo(_context.DateSnippets, new ODataQuerySettings());;

    //Exception when using $expand.. cannot cast SelectAllAndExpand<DateSnippet> to DateSnippet
    List<DateSnippet> dateSnippets = query.Cast<DateSnippet>().ToList();

    var dateSnippetsViewModels = (from d in dateSnippets
                                    select new DateSnippetWithDepartmentsViewModel
                                    {
                                        ...
                                    });

    var result = new PageResult<DateSnippetWithDepartmentsViewModel>(
            dateSnippetsViewModels as IEnumerable<DateSnippetWithDepartmentsViewModel>,
            Request.GetNextPageLink(),
            Request.GetInlineCount());

    return result;
}

Ответ 1

Попробуйте это. Надеемся, что мы будем работать, к тому времени, когда мы перейдем к Перечислителю, результат должен быть DateSnippet. То, что вы делали раньше, пыталось применить в дереве Linq Expression. Я подозреваю, что в IQueryable Execute, который разрешен и преобразован в отличие от cast.

public PageResult<DateSnippetWithDepartmentsViewModel> GetDatesWithDepartments(ODataQueryOptions<DateSnippet> options)
{
    IQueryable query = options.ApplyTo(_context.DateSnippets, new ODataQuerySettings());;

    List<DateSnippet> dateSnippets = new List<DateSnippet>();
    foreach(DateSnippet item in query)
    {
        dateSnippets.Add(item);
    }

    var dateSnippetsViewModels = (from d in dateSnippets
                                    select new DateSnippetWithDepartmentsViewModel
                                    {
                                        ...
                                    });

    var result = new PageResult<DateSnippetWithDepartmentsViewModel>(
            dateSnippetsViewModels as IEnumerable<DateSnippetWithDepartmentsViewModel>,
            Request.GetNextPageLink(),
            Request.GetInlineCount());

    return result;
}