4

I have setup a Web API 2.2 ODataController such that I can process my OData options manually (i.e. Without [EnableQuery] and or using a ODataQueryOptions parameter). However I have run into what looks like a bug. Given the following code:

public IHttpActionResult GetEmployees() {
//Get Queryable Item (in this case just an in-memory List made queryable)
  IQueryable<Employee> employees = _Employees.AsQueryable();

//Get Requested URI without querystring (there may be other ways of doing this)
  String newUri = Request.RequestUri.AbsoluteUri;
  if (!String.IsNullOrEmpty(Request.RequestUri.Query)) {
    newUri = newUri.Replace(Request.RequestUri.Query, "");
  }

//Add custom OData querystring (this is for example purposes)
  newUri = String.Format("{0}?$skip={1}&$top={2}", newUri, 1, 1);

//Create new HttpRequestMessage from the updated URI
  HttpRequestMessage newRequest = new HttpRequestMessage(Request.Method, newUri);

//Create new ODataQueryContext based off initial request (required to create ODataQueryOptions)
  ODataQueryContext newContext = new ODataQueryContext(Request.ODataProperties().Model, typeof(Employee), Request.ODataProperties().Path);

//Create new ODataQueryOptions based off new context and new request
  ODataQueryOptions<Employee> newOptions = new ODataQueryOptions<Employee>(newContext, newRequest);

//Apply the new ODataQueryOptions to the Queryable Item
  employees = newOptions.ApplyTo(employees) as IQueryable<Employee>;

//Return List (will be serialized by OData formatter)
  return Ok(employees.ToList());
}

Which works 100%, however adding a $select or $expand like this:

newUri = String.Format("{0}?$skip={1}&$top={2}&$expand=Projects", newUri, 1, 1);

will return null from

employees = newOptions.ApplyTo(employees) as IQueryable<Employee>;

which has forced me to create two separate ODataQueryOptions, one to applyTo the IQueryable (without any $select or $expand), and another with just the $selects/$expands to build the SelectExpandClause to assign to Request.ODataProperties().SelectExpandClause.

I just don't understand why the null return is happening. The core intent behind this code is to allow for better control over processing OData when working with ORMs other than Entity Framework. So realistically I'd end up overriding applyTo anyways (or just manually processing the expression tree myself), but this particular example still seems like a bug to me.

Can anyone give me some insight on this? Maybe there is just something I'm missing.

4

1 回答 1

5

(将我上面的评论移至答案)

因为你真正从 ApplyTo 得到的(一旦你添加 $select 或 $expand)是

System.Web.OData.Query.Expressions.SelectExpandBinder.SelectAllAndExpand<Employe‌​e>

当然,它不能转换为 IQueryable,因此为空。

为什么不添加 EnableQuery 属性,并返回一个 IQueryable(而不是 ToList)?

于 2015-05-27T05:43:17.640 回答