Entity framework core OData扩展中包含$top或$skip的InvalidOperationException

Entity framework core OData扩展中包含$top或$skip的InvalidOperationException,entity-framework-core,odata,automapper,Entity Framework Core,Odata,Automapper,我们将EF Core 3.1与OData 7.5.1一起使用。我们还使用DTO和Automapper 10.1.1将我们的实体映射到这些DTO 我尝试使用以下查询仅展开嵌套集合中的前两个项: https://localhost:44347/v1/odata/Subcategories?$top=3$expand=Products($top=2) 如果我在实体上而不是DTO上运行此查询,那么在Expand中添加的所有查询选项都可以正常工作 但是,如果我们在ProjectTo之后在DTO上运行此操作

我们将EF Core 3.1与OData 7.5.1一起使用。我们还使用DTO和Automapper 10.1.1将我们的实体映射到这些DTO

我尝试使用以下查询仅展开嵌套集合中的前两个项:

https://localhost:44347/v1/odata/Subcategories?$top=3$expand=Products($top=2)

如果我在实体上而不是DTO上运行此查询,那么在Expand中添加的所有查询选项都可以正常工作

但是,如果我们在ProjectTo之后在DTO上运行此操作,我会收到以下异常:

[为简洁起见缩短]

System.InvalidOperationException: Processing of the LINQ expression '(ProjectionBindingExpression: 0)' by 'RelationalProjectionBindingExpressionVisitor' failed. This may indicate either a bug or a limitation in EF Core. See https://go.microsoft.com/fwlink/?linkid=2101433 for more detailed information.
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.VisitExtension(Expression extensionExpression)
   at System.Linq.Expressions.Expression.Accept(ExpressionVisitor visitor)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Visit(Expression expression)
   at System.Linq.Expressions.ExpressionVisitor.VisitConditional(ConditionalExpression node)
   at System.Linq.Expressions.ConditionalExpression.Accept(ExpressionVisitor visitor)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Visit(Expression expression)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.VisitMemberAssignment(MemberAssignment memberAssignment)
   at System.Linq.Expressions.ExpressionVisitor.VisitMemberBinding(MemberBinding node)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.VisitMemberInit(MemberInitExpression memberInitExpression)
   at System.Linq.Expressions.MemberInitExpression.Accept(ExpressionVisitor visitor)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Visit(Expression expression)
所以,这是有效的

        [AllowAnonymous, HttpGet]
        public async Task<IActionResult> Get(ODataQueryOptions<ProductSubcategoryDto> options)
        {
            IQueryable<ProductSubcategory> subs = DbContext.ProductSubcategories;
   
            IQueryable queryable = options.ApplyTo(subs); 
   
            return Ok(queryable);    
        }
[AllowAnonymous,HttpGet]
公共异步任务获取(ODataQueryOptions选项)
{
IQueryable subs=DbContext.ProductSubcategories;
IQueryable queryable=options.ApplyTo(subs);
返回Ok(可查询);
}
但这一个扔

        [AllowAnonymous, HttpGet]
        public async Task<IActionResult> Get(ODataQueryOptions<ProductSubcategoryDto> options)
        {   
            IQueryable<ProductSubcategoryDto> subsDto = DbContext.ProductSubcategories.ProjectTo<ProductSubcategoryDto>(Mapper.ConfigurationProvider);

            IQueryable queryable = options.ApplyTo(subsDto);    

            return Ok(queryable);
        }
[AllowAnonymous,HttpGet]
公共异步任务获取(ODataQueryOptions选项)
{   
IQueryable subsDto=DbContext.ProductSubcategories.ProjectTo(Mapper.ConfigurationProvider);
IQueryable queryable=options.ApplyTo(subsDto);
返回Ok(可查询);
}
我还尝试了可查询扩展,扩展中的查询选项被完全忽略,除了$select

        [AllowAnonymous, HttpGet]
        public async Task<IActionResult> Get(ODataQueryOptions<ProductSubcategoryDto> options)
        {
             return Ok(await DbContext.ProductSubcategories.GetQueryAsync(Mapper, options));
        }
[AllowAnonymous,HttpGet]
公共异步任务获取(ODataQueryOptions选项)
{
返回Ok(等待DbContext.ProductSubcategories.GetQueryAsync(映射器,选项));
}
在这种情况下,我们所有的DTO和ProjectTo调用都可以正常工作


我做的一切都对吗?这是EF Core或Automapper的错误吗?

您是否有用于扩展产品的映射器?谢谢@LucianBargaoanu。我已经试过了,可查询扩展似乎也忽略了扩展中的$skip和$top。我也刚在那里开业。@Stutje是的,我是。其他地方的地图都很好。从Product到ProductDto的映射非常简单。我已经找到了Queryable扩展忽略这些查询的原因。这是因为我们在构建过程中在EDM上调用EnableLowerCamelCase,绑定成员名称不会与更新的名称进行比较,而是与扩展的原始Pascal大小写进行比较。详情见附件。