Как я могу разобрать ODataQueryOptions из строки? - PullRequest
0 голосов
/ 20 апреля 2020

Я должен предоставить некоторые конечные точки чтения для наших сущностей EF6 в API ASP. NET, которые соответствуют спецификации OData. Поиск сущностей хорошо работает на основе функций, которые принимают экземпляр System.Web.Http.OData.Query.ODataQueryOptions<TEntity>.

Теперь, согласно документам, реализация OData не поддерживает $count.

* 1008. * Однако мы хотели бы предложить, по крайней мере, возможность извлечения общего количества (отфильтрованного) набора данных, как показано в документах , например (путем небольшого объединения нескольких из этих выборок):
http://host/service/Products/$count($filter=Price gt 5.00)

(Исходя из спецификации c, я понимаю, что это должен быть действительный, совместимый со спецификацией запрос OData для количества продуктов, цена которых превышает 5¤. Пожалуйста, исправьте меня, если я неправильно.)

Теперь получить счет на основе IQueryable, возвращенного из ODataQuerySettings.ApplyTo, тривиально. Также захватывает запросов на этот маршрут:

[Route("$count({queryOptions})")]
public int Count(ODataQueryOptions<ProductEntity> queryOptions)

Единственный недостающий бит - это то, что часть маршрута queryOptions должна быть проанализирована в экземпляре ODataQueryOptions<ProductEntity>. На других конечных точках OData это работает без лишних слов. Однако, даже когда я вызываю эту конечную точку с $filter, все, что я получаю, это «пустой» (т.е. инициализированный по умолчанию) ODataQueryOptions<ProductEntity> экземпляр без установленного фильтра.

В качестве альтернативы, я могу объявить моя конечная точка веб-API выглядит следующим образом:

[Route("$count({queryOptions})")]
public int Count(string rawQueryOptions)

В этом методе rawQueryOptions содержит параметры запроса, которые я буду sh передавать в OData, то есть анализировать для заполнения экземпляра ODataQueryOptions<ProductEntity>.

Это должно быть очень просто, как то же самое происходит для любой другой конечной точки OData. Для сравнения:

[Route("")]
public IEnumerable<object> Filter(ODataQueryOptions<ProductEntity> queryOptions)

Это работает; параметры запроса заполняются, как и ожидалось, в отличие от случая с моей конечной точкой.

Как я могу заполнить свой экземпляр параметров запроса OData на основе строки, извлеченной из моего маршрута?

Ещё несколько вещей, которые я пробовал:

  • Применено [FromUri] к параметру queryOptions.
  • Применено [ODataQueryParameterBinding] к параметру queryOptions.
...