【问题标题】:Entity Framework 4 simple Compiled Query internal exception on compilationEntity Framework 4 simple Compiled Query 编译时的内部异常
【发布时间】:2010-06-02 09:46:52
【问题描述】:

我想从排序表中检索一页。我希望在服务器上完成排序和分页。为此,我创建了以下编译查询:

internal static readonly Func<MyEntities, string, int, int, IQueryable<Model.Message>> MessagesPagedSortedByDateQuery =
        CompiledQuery.Compile((MyEntities db, string folderId, int pageSize, int pageIndex) =>
        (
            db.Messages.Where(m => m.FolderId == folderId).OrderBy(m => m.Date).Skip(pageSize * pageIndex).Take(pageSize)
        ));

这对我来说似乎是一个非常简单的问题。但是,当我使用以下语句执行它时:

var messages = MessageCompiledQueries.MessagesPagedSortedByDateQuery(myEntities, folderId, pageSize, pageIndex).ToList();

我从源 System.Data.Entity 得到以下异常:

Count 必须是 DbConstantExpression 或 DbParameterReferenceExpression。 参数名称:计数

有了这个堆栈跟踪:

在 System.Data.Common.CommandTrees.ExpressionBuilder.Internal.ArgumentValidation.ValidateSkip(DbExpressionBinding input, IEnumerable'1 sortOrder, DbExpression count) 在 System.Data.Common.CommandTrees.ExpressionBuilder.DbExpressionBuilder.Skip(DbExpressionBinding 输入,IEnumerable'1 sortOrder,DbExpression 计数) 在 System.Data.Objects.ELinq.ExpressionConverter.OrderByLifter.ApplySortOrderToSkip(DbExpression 输入,DbSortExpression 排序,DbExpression k) 在 System.Data.Objects.ELinq.ExpressionConverter.OrderByLifter.SortLifter.Skip(DbExpression k) 在 System.Data.Objects.ELinq.ExpressionConverter.Skip(DbExpressionBinding 输入,DbExpression skipCount) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SkipTranslator.TranslatePagingOperator(ExpressionConverter 父,DbExpression 操作数,DbExpression 计数) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.PagingTranslator.TranslateUnary(ExpressionConverter 父,DbExpression 操作数,MethodCallExpression 调用) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.UnarySequenceMethodTranslator.Translate(ExpressionConverter parent,MethodCallExpression 调用) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter 父,MethodCallExpression 调用,SequenceMethod 序列方法) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter 父,MethodCallExpression linq) 在 System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator'1.Translate(ExpressionConverter parent,Expression linq) 在 System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(表达式 linq) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.UnarySequenceMethodTranslator.Translate(ExpressionConverter parent,MethodCallExpression 调用) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter 父,MethodCallExpression 调用,SequenceMethod 序列方法) 在 System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter 父,MethodCallExpression linq) 在 System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator'1.Translate(ExpressionConverter parent,Expression linq) 在 System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(表达式 linq) 在 System.Data.Objects.ELinq.ExpressionConverter.Convert() 在 System.Data.Objects.ELinq.CompiledELinqQueryState.GetExecutionPlan(Nullable'1 forMergeOption) 在 System.Data.Objects.ObjectQuery'1.GetResults(Nullable'1 forMergeOption) 在 System.Data.Objects.ObjectQuery'1.System.Collections.Generic.IEnumerable.GetEnumerator() 在 System.Collections.Generic.List'1..ctor(IEnumerable'1 集合) 在 System.Linq.Enumerable.ToList[TSource](IEnumerable'1 源) 在 MyApp.Data.Repository.MessageRepository.GetByFolder(String folderId, Int32 pageSize, Int32 pageIndex, String sortField) 在 C:\Projects\MyApp\MyApp.Data\Repository\MessageRepository.cs:line 40 在 C:\Projects\MyApp\MyApp.WebClient\Controllers\FolderController.cs:line 53 中的 MyApp.WebClient.Controllers.FolderController.Messages(GridCommand command, String folderId) 在 lambda_method(闭包,ControllerBase,对象 []) 在 System.Web.Mvc.ActionMethodDispatcher.Execute(ControllerBase 控制器,Object[] 参数) 在 System.Web.Mvc.ReflectedActionDescriptor.Execute(ControllerContext 控制器上下文,IDictionary`2 参数) 在 System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary'2 参数) 在 System.Web.Mvc.ControllerActionInvoker.c__DisplayClassd.b__a() 在 System.Web.Mvc.ControllerActionInvoker.InvokeActionMethodFilter(IActionFilter 过滤器,ActionExecutingContext preContext,Func'1 延续)

第一次编译查询时似乎发生了异常。如果我从查询中删除 orderby,它就可以正常工作。但显然我希望在服务器上进行排序和分页,所以我不想在检索完整表后这样做。这是实体框架中的错误吗?我在网上找不到任何关于它的信息。有人知道如何解决这个问题吗? 我在 Visual Studio 2010 中使用 .Net Framework 4 最终版本。

谢谢!

【问题讨论】:

    标签: .net entity-framework compiled-query


    【解决方案1】:

    看看这是否能解决问题:

    internal static readonly Func<MyEntities, string, int, int, int, IQueryable<Model.Message>> 
        MessagesPagedSortedByDateQuery =
            CompiledQuery.Compile((MyEntities db, string folderId, int pageSize, int pageIndex, int skipCount) =>
            (
                db.Messages.Where(m => m.FolderId == folderId).OrderBy(m => m.Date).Skip(skipCount).Take(pageSize)
            ));
    

    请注意,我已更改签名。这显然不是一个理想的解决方案,但我还没有看到您如何在代码上下文中使用它。如果它可以解决错误,您可以将其调整为更有用的东西。

    【讨论】:

    • 太棒了!这行得通。就像你说的那样,这并不理想,但我很高兴有一个解决方法。我非常惊讶像这样的简单查询会为实体框架造成这样的问题,而普通开发人员很难确定问题出在乘法上。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-13
    • 2023-03-08
    相关资源
    最近更新 更多