asp.net-web-api - Microsoft.AspNet.OData [EnableQueryAttribute] 与 [Route] 属性结合时失败
问题描述
我正在使用 nuget 包 Microsoft.AspNet.OData 6.1.0。创建启用 odata 的操作。我在以下设置中遇到了 [Route] 属性的问题。
// The Setup
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
// configure non odata ...
//OData support
config.AddODataQueryFilter();
config.EnableDependencyInjection();
ODataConventionModelBuilder builder = new ODataConventionModelBuilder();
builder.EnableLowerCamelCase(NameResolverOptions.ProcessReflectedPropertyNames | NameResolverOptions.ProcessExplicitPropertyNames);
builder.EntitySet<MixedRealityCatalogItem>("KISS");
var edmModel = builder.GetEdmModel();
config.MapODataServiceRoute("ODataRoute", "/", edmModel);
config.Count().Filter().OrderBy().Select().MaxTop(2000);
}
}
// The Controller
public class KISSController : ApiController
{
public KISSController(IRepository<MixedRealityCatalogItem> repository)
{
this.Repository = repository ?? throw new ArgumentNullException(nameof(repository));
}
private IRepository<MixedRealityCatalogItem> Repository { get; set; }
[EnableQuery(PageSize = 2000, MaxAnyAllExpressionDepth = 2)]
[HttpGet]
[Route("KISS")] // <-- this causes and exception
public IEnumerable<MixedRealityCatalogItem> GetAll(ODataQueryOptions<MixedRealityCatalogItem> options)
{
IQueryable<MixedRealityCatalogItem> results = this.Repository.GetAll();
var settings = new ODataQuerySettings
{
HandleNullPropagation = HandleNullPropagationOption.False,
EnableConstantParameterization = false,
EnsureStableOrdering = false
};
//Builds, but does not execute the Iqueryable
IQueryable finalQuery = options.ApplyTo(results, settings);
var finalResults = new List<MixedRealityCatalogItem>();
//Will actually execute the query against the DB
foreach (MixedRealityCatalogItem item in finalQuery)
{
finalResults.Add(item);
}
return finalResults;
}
}
如果我注释掉 Route 属性,则 GetAll 操作适用于所有查询,但如果存在 route 属性,则当我每个用户使用一个评估“任何”语句的过滤器时,我都会收到以下异常。
{
"Message": "An error has occurred.",
"ExceptionMessage": "Value cannot be null.\r\nParameter name: type",
"ExceptionType": "System.ArgumentNullException",
"StackTrace": " at System.Linq.Expressions.Expression.Parameter(Type type, String name)\r\n at System.Web.OData.Query.Expressions.FilterBinder.HandleLambdaParameters(IEnumerable`1 rangeVariables)\r\n at System.Web.OData.Query.Expressions.FilterBinder.BindAnyNode(AnyNode anyNode)\r\n at System.Web.OData.Query.Expressions.FilterBinder.BindExpression(SingleValueNode expression, RangeVariable rangeVariable, Type elementType)\r\n at System.Web.OData.Query.Expressions.FilterBinder.BindFilterClause(FilterBinder binder, FilterClause filterClause, Type filterType)\r\n at System.Web.OData.Query.FilterQueryOption.ApplyTo(IQueryable query, ODataQuerySettings querySettings)\r\n at System.Web.OData.Query.ODataQueryOptions.ApplyTo(IQueryable query, ODataQuerySettings querySettings)\r\n at AssetManager.Api.Controllers.Contracts.KISSController.GetAll(ODataQueryOptions`1 options) in D:\\git\\LSource\\AssetManagerAPI\\src\\AssetManager.Web\\Controllers\\Contracts\\AssetManagerBaseApiController.cs:line 48\r\n at lambda_method(Closure , Object , Object[] )\r\n at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ActionExecutor.<>c__DisplayClass10.<GetExecutor>b__9(Object instance, Object[] methodParameters)\r\n at System.Web.Http.Controllers.ReflectedHttpActionDescriptor.ExecuteAsync(HttpControllerContext controllerContext, IDictionary`2 arguments, CancellationToken cancellationToken)\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Controllers.ApiControllerActionInvoker.<InvokeActionAsyncCore>d__0.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Filters.ActionFilterAttribute.<CallOnActionExecutedAsync>d__5.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Web.Http.Filters.ActionFilterAttribute.<CallOnActionExecutedAsync>d__5.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Filters.ActionFilterAttribute.<ExecuteActionFilterAsyncCore>d__0.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Controllers.ActionFilterResult.<ExecuteAsync>d__2.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Controllers.AuthenticationFilterResult.<ExecuteAsync>d__0.MoveNext()\r\n--- End of stack trace from previous location where exception was thrown ---\r\n at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()\r\n at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)\r\n at System.Web.Http.Dispatcher.HttpControllerDispatcher.<SendAsync>d__1.MoveNext()"
}
我究竟做错了什么?在这个简单的示例中,路由属性不是必需的,但在我的实际情况下它很重要。
笔记:
解决方案
事实证明存在与 DataContract 属性相关的错误,该错误已在 7.0.0 版中修复
修复错误的拉取请求:https ://github.com/OData/WebApi/pull/1484
带有错误修复的 Nuget 版本:https ://www.nuget.org/packages/Microsoft.AspNet.OData/7.0.0
推荐阅读
- javascript - 在 Electron 上将正文添加到 ClientRequest
- java - 从地图对象中查找范围内的元素数
- .htaccess - 显示错误 404 .htaccess 的空参数
- ios - Firebase - for loop Swift 内嵌套的 observeSingleEvent 方法
- django - 如何在基于类的视图中有多个发布请求处理方法
- node.js - 带有 ExpressJS 的 NodeJS
- powershell - 在 if 语句中组合多个条件
- extjs - 重新计算模型的字段
- haskell - 使用 Haskell 读取 OBJ 文件
- python - python setup.py 在没有 sudo 的情况下安装在 anaconda 中