在实体框架核心v3.1.4中使用Take()LINQ方法

问题描述 投票:0回答:1

我正在尝试在我的API请求中添加一个限制GET查询参数(即?limit = 10),然后Take() LINQ方法将使用此限制的值来仅获取我想要的结果数。我要做的是将LINQ Take()方法作为LINQ-TO-T-SQL查询的一部分包括在内,并执行限制作为SQL查询的一部分。我在下面尝试了以下代码。我还捕获了错误堆栈跟踪。

代码1:对于此代码,我正在尝试在查询的顶级资源上使用Take()。然后,然后(在q的声明中),我将执行与顶层资源相关的子查询。

baseQuery = baseQuery.Take(2);

var q = from doctor in baseQuery

        let sp = (from ds in db.DoctorSpecialty
                  join s in db.Specialty on ds.SpecialtyID equals s.SpecialtyID
                  where ds.DoctorID == doctor.DoctorID
                  select new
                  {
                      s.SpecialtyID,
                      s.Specialty1
                  }).ToList()

        let clinics = (from c in db.Clinic
                  where c.DoctorID == doctor.DoctorID && c.Active == true

                  let schedule = (from sc in db.Schedule
                                  where sc.ClinicID == c.ClinicID
                                    && sc.DoctorID == doctor.DoctorID
                                    && DoctorDirectoryConstants.ValidScheduleNotes.Contains(sc.Notes)
                                  select sc).ToList()

                  select new
                  {
                      c.ClinicID,
                      c.Street,
                      c.ClinicName,
                      c.ContactNumber,
                      c.City,
                      c.Province,
                      c.HomeNumber,
                      c.MobileNumber,
                      c.WorkNumber,
                      c.Email,
                      Schedules = schedule,
                  }).ToList() 
        select new
        {
            Doctor = doctor,
            Specialties = sp,
            Clinics = clinics

        };

var rs = q.ToList();

代码1的错误堆栈跟踪:

fail: Microsoft.EntityFrameworkCore.Database.Command[20102]
      Failed executing DbCommand (5ms) [Parameters=[@__p_0='?' (DbType = Int32)], CommandType='Text', CommandTimeout='30']
      SELECT [t].[DoctorID], [t].[Address], [t].[AvailableInvites], [t].[Birthdate], [t].[City], [t].[CityID], [t].[ContactNumber], [t].[Country], [t].[DateRegistered], [t].[Description], [t].[DoctorUrl], [t].[Email], [t].[EmailActivated], [t].[EmailUID], [t].[EmailVerifiedFirstTime], [t].[Facebook], [t].[FirstName], [t].[Gender], [t].[GooglePlus], [t].[HomeNumber], [t].[Image], [t].[LastName], [t].[LinkedIn], [t].[MainSpecialty], [t].[ManuallyVerified], [t].[MedicalSchool], [t].[MedicalSchoolYear], [t].[MiddleName], [t].[MobileNumber], [t].[Nationality], [t].[OriginalIssueDate], [t].[PRCNumber], [t].[PageOkay], [t].[PatientNumber], [t].[PhicNumber], [t].[PractisingSince], [t].[Province], [t].[PtrNumber], [t].[Residency], [t].[ResidencyYear], [t].[S2Number], [t].[ShowPublicProfile], [t].[Status], [t].[Street], [t].[Suffix], [t].[Title], [t].[Twitter], [t].[UserID], [t].[Website], [t].[WorkNumber], [t].[Zipcode], [t0].[SpecialtyID], [t0].[Specialty], [t0].[Id], [t2].[ClinicID], [t2].[Street], [t2].[ClinicName], [t2].[ContactNumber], [t2].[City], [t2].[Province], [t2].[HomeNumber], [t2].[MobileNumber], [t2].[WorkNumber], [t2].[Email], [t2].[ScheduleID], [t2].[Active], [t2].[ClinicID0], [t2].[DateModified], [t2].[DayOfWeek], [t2].[DoctorID], [t2].[Notes], [t2].[StartFrom], [t2].[TimeEnd], [t2].[TimeStart], [t2].[Until]
      FROM (
          SELECT TOP(@__p_0) [d].[DoctorID], [d].[Address], [d].[AvailableInvites], [d].[Birthdate], [d].[City], [d].[CityID], [d].[ContactNumber], [d].[Country], [d].[DateRegistered], [d].[Description], [d].[DoctorUrl], [d].[Email], [d].[EmailActivated], [d].[EmailUID], [d].[EmailVerifiedFirstTime], [d].[Facebook], [d].[FirstName], [d].[Gender], [d].[GooglePlus], [d].[HomeNumber], [d].[Image], [d].[LastName], [d].[LinkedIn], [d].[MainSpecialty], [d].[ManuallyVerified], [d].[MedicalSchool], [d].[MedicalSchoolYear], [d].[MiddleName], [d].[MobileNumber], [d].[Nationality], [d].[OriginalIssueDate], [d].[PRCNumber], [d].[PageOkay], [d].[PatientNumber], [d].[PhicNumber], [d].[PractisingSince], [d].[Province], [d].[PtrNumber], [d].[Residency], [d].[ResidencyYear], [d].[S2Number], [d].[ShowPublicProfile], [d].[Status], [d].[Street], [d].[Suffix], [d].[Title], [d].[Twitter], [d].[UserID], [d].[Website], [d].[WorkNumber], [d].[Zipcode]
          FROM [Doctor] AS [d]
          WHERE [d].[Status] = 'good'
      ) AS [t]
      LEFT JOIN (
          SELECT [s].[SpecialtyID], [s].[Specialty], [d0].[Id], [d0].[DoctorID]
          FROM [DoctorSpecialty] AS [d0]
          INNER JOIN [Specialty] AS [s] ON [d0].[SpecialtyID] = [s].[SpecialtyID]
      ) AS [t0] ON [t].[DoctorID] = [t0].[DoctorID]
      LEFT JOIN (
          SELECT [c].[ClinicID], [c].[Street], [c].[ClinicName], [c].[ContactNumber], [c].[City], [c].[Province], [c].[HomeNumber], [c].[MobileNumber], [c].[WorkNumber], [c].[Email], [t1].[ScheduleID], [t1].[Active], [t1].[ClinicID] AS [ClinicID0], [t1].[DateModified], [t1].[DayOfWeek], [t1].[DoctorID], [t1].[Notes], [t1].[StartFrom], [t1].[TimeEnd], [t1].[TimeStart], [t1].[Until], [c].[DoctorID] AS [DoctorID0]
          FROM [Clinic] AS [c]
          LEFT JOIN (
              SELECT [s0].[ScheduleID], [s0].[Active], [s0].[ClinicID], [s0].[DateModified], [s0].[DayOfWeek], [s0].[DoctorID], [s0].[Notes], [s0].[StartFrom], [s0].[TimeEnd], [s0].[TimeStart], [s0].[Until]
              FROM [Schedule] AS [s0]
              WHERE ([s0].[DoctorID] = [d].[DoctorID]) AND [s0].[Notes] IN (N'Walk-In', N'By Appointment')
          ) AS [t1] ON [c].[ClinicID] = [t1].[ClinicID]
          WHERE [c].[Active] = CAST(1 AS bit)
      ) AS [t2] ON [t].[DoctorID] = [t2].[DoctorID0]
      ORDER BY [t].[DoctorID], [t0].[Id], [t0].[SpecialtyID], [t2].[ClinicID], [t2].[ScheduleID]
fail: Microsoft.EntityFrameworkCore.Query[10100]
      An exception occurred while iterating over the results of a query for context type 'SeriousMDCommonsCore.Models.Database.SeriousmdEntitiesContext'.
      Microsoft.Data.SqlClient.SqlException (0x80131904): The multi-part identifier "d.DoctorID" could not be bound.
         at Microsoft.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
         at Microsoft.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
         at Microsoft.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj, Boolean callerHasConnectionLock, Boolean asyncClose)
         at Microsoft.Data.SqlClient.TdsParser.TryRun(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj, Boolean& dataReady)
         at Microsoft.Data.SqlClient.SqlDataReader.TryConsumeMetaData()
         at Microsoft.Data.SqlClient.SqlDataReader.get_MetaData()
         at Microsoft.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString, Boolean isInternal, Boolean forDescribeParameterEncryption, Boolean shouldCacheForAlwaysEncrypted)
         at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean isAsync, Int32 timeout, Task& task, Boolean asyncWrite, Boolean inRetry, SqlDataReader ds, Boolean describeParameterEncryptionRequest)
         at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, TaskCompletionSource`1 completion, Int32 timeout, Task& task, Boolean& usedCache, Boolean asyncWrite, Boolean inRetry, String method)
         at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method)
         at Microsoft.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior)
         at Microsoft.Data.SqlClient.SqlCommand.ExecuteDbDataReader(CommandBehavior behavior)
         at System.Data.Common.DbCommand.ExecuteReader()
         at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReader(RelationalCommandParameterObject parameterObject)
         at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.InitializeReader(DbContext _, Boolean result)
         at Microsoft.EntityFrameworkCore.SqlServer.Storage.Internal.SqlServerExecutionStrategy.Execute[TState,TResult](TState state, Func`3 operation, Func`3 verifySucceeded)
         at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.MoveNext()
      ClientConnectionId:0b10b611-bd0f-4fcb-a543-fdbe530fc029
      Error Number:4104,State:1,Class:16
Microsoft.Data.SqlClient.SqlException (0x80131904): The multi-part identifier "d.DoctorID" could not be bound.
   at Microsoft.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
   at Microsoft.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
   at Microsoft.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj, Boolean callerHasConnectionLock, Boolean asyncClose)
   at Microsoft.Data.SqlClient.TdsParser.TryRun(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj, Boolean& dataReady)
   at Microsoft.Data.SqlClient.SqlDataReader.TryConsumeMetaData()
   at Microsoft.Data.SqlClient.SqlDataReader.get_MetaData()
   at Microsoft.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString, Boolean isInternal, Boolean forDescribeParameterEncryption, Boolean shouldCacheForAlwaysEncrypted)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean isAsync, Int32 timeout, Task& task, Boolean asyncWrite, Boolean inRetry, SqlDataReader ds, Boolean describeParameterEncryptionRequest)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, TaskCompletionSource`1 completion, Int32 timeout, Task& task, Boolean& usedCache, Boolean asyncWrite, Boolean inRetry, String method)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method)
   at Microsoft.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior)
   at Microsoft.Data.SqlClient.SqlCommand.ExecuteDbDataReader(CommandBehavior behavior)
   at System.Data.Common.DbCommand.ExecuteReader()
   at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReader(RelationalCommandParameterObject parameterObject)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.InitializeReader(DbContext _, Boolean result)
   at Microsoft.EntityFrameworkCore.SqlServer.Storage.Internal.SqlServerExecutionStrategy.Execute[TState,TResult](TState state, Func`3 operation, Func`3 verifySucceeded)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.MoveNext()
ClientConnectionId:0b10b611-bd0f-4fcb-a543-fdbe530fc029
Error Number:4104,State:1,Class:16
fail: Microsoft.AspNetCore.Server.Kestrel[13]
      Connection id "0HM03JVLBFS8O", Request id "0HM03JVLBFS8O:00000001": An unhandled exception was thrown by the application.
Microsoft.Data.SqlClient.SqlException (0x80131904): The multi-part identifier "d.DoctorID" could not be bound.
   at Microsoft.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
   at Microsoft.Data.SqlClient.SqlInternalConnection.OnError(SqlException exception, Boolean breakConnection, Action`1 wrapCloseInAction)
   at Microsoft.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj, Boolean callerHasConnectionLock, Boolean asyncClose)
   at Microsoft.Data.SqlClient.TdsParser.TryRun(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj, Boolean& dataReady)
   at Microsoft.Data.SqlClient.SqlDataReader.TryConsumeMetaData()
   at Microsoft.Data.SqlClient.SqlDataReader.get_MetaData()
   at Microsoft.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString, Boolean isInternal, Boolean forDescribeParameterEncryption, Boolean shouldCacheForAlwaysEncrypted)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean isAsync, Int32 timeout, Task& task, Boolean asyncWrite, Boolean inRetry, SqlDataReader ds, Boolean describeParameterEncryptionRequest)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, TaskCompletionSource`1 completion, Int32 timeout, Task& task, Boolean& usedCache, Boolean asyncWrite, Boolean inRetry, String method)
   at Microsoft.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method)
   at Microsoft.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior)
   at Microsoft.Data.SqlClient.SqlCommand.ExecuteDbDataReader(CommandBehavior behavior)
   at System.Data.Common.DbCommand.ExecuteReader()
   at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReader(RelationalCommandParameterObject parameterObject)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.InitializeReader(DbContext _, Boolean result)
   at Microsoft.EntityFrameworkCore.SqlServer.Storage.Internal.SqlServerExecutionStrategy.Execute[TState,TResult](TState state, Func`3 operation, Func`3 verifySucceeded)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.Enumerator.MoveNext()
   at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
   at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
   at lambda_method(Closure , Object , Object[] )
   at Microsoft.Extensions.Internal.ObjectMethodExecutor.Execute(Object target, Object[] parameters)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ActionMethodExecutor.SyncObjectResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, Object controller, Object[] arguments)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeActionMethodAsync()
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeNextActionFilterAsync()
--- End of stack trace from previous location where exception was thrown ---
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Rethrow(ActionExecutedContextSealed context)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeInnerFilterAsync()
--- End of stack trace from previous location where exception was thrown ---
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeFilterPipelineAsync>g__Awaited|19_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
   at Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
   at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequests[TContext](IHttpApplication`1 application)
ClientConnectionId:0b10b611-bd0f-4fcb-a543-fdbe530fc029
Error Number:4104,State:1,Class:16

代码2:这里,不是在Take()中执行baseQuery,而是在最终查询表达式Take()中执行q。我还添加了doctor.DoctorID作为某种类型的id,我认为需要将其提供给Take() LINQ方法

var q = from doctor in baseQuery

        let sp = (from ds in db.DoctorSpecialty
                  join s in db.Specialty on ds.SpecialtyID equals s.SpecialtyID
                  where ds.DoctorID == doctor.DoctorID
                  select new
                  {
                      s.SpecialtyID,
                      s.Specialty1
                  }).ToList()

        let clinics = (from c in db.Clinic
                  where c.DoctorID == doctor.DoctorID && c.Active == true

                  let schedule = (from sc in db.Schedule
                                  where sc.ClinicID == c.ClinicID
                                    && sc.DoctorID == doctor.DoctorID
                                    && DoctorDirectoryConstants.ValidScheduleNotes.Contains(sc.Notes)
                                  select sc).ToList()

                  select new
                  {
                      c.ClinicID,
                      c.Street,
                      c.ClinicName,
                      c.ContactNumber,
                      c.City,
                      c.Province,
                      c.HomeNumber,
                      c.MobileNumber,
                      c.WorkNumber,
                      c.Email,
                      Schedules = schedule,
                  }).ToList() 
        select new
        {
            doctor.DoctorID,
            Doctor = doctor,
            Specialties = sp,
            Clinics = clinics

        };

q = q.Take(2);

var rs = q.ToList();

代码2的错误堆栈跟踪,这里的错误与代码2的错误有所不同,似乎Take() LINQ方法正在使用添加的索引,但仍会引发错误。

fail: Microsoft.AspNetCore.Server.Kestrel[13]
      Connection id "0HM03K296O68T", Request id "0HM03K296O68T:00000001": An unhandled exception was thrown by the application.
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 System.Linq.Expressions.ExpressionVisitor.Visit(Expression node)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Visit(Expression expression)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.VisitNew(NewExpression newExpression)
   at System.Linq.Expressions.NewExpression.Accept(ExpressionVisitor visitor)
   at System.Linq.Expressions.ExpressionVisitor.Visit(Expression node)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Visit(Expression expression)
   at Microsoft.EntityFrameworkCore.Query.Internal.RelationalProjectionBindingExpressionVisitor.Translate(SelectExpression selectExpression, Expression expression)
   at Microsoft.EntityFrameworkCore.Query.RelationalQueryableMethodTranslatingExpressionVisitor.TranslateSelect(ShapedQueryExpression source, LambdaExpression selector)
   at Microsoft.EntityFrameworkCore.Query.QueryableMethodTranslatingExpressionVisitor.VisitMethodCall(MethodCallExpression methodCallExpression)
   at Microsoft.EntityFrameworkCore.Query.RelationalQueryableMethodTranslatingExpressionVisitor.VisitMethodCall(MethodCallExpression methodCallExpression)
   at System.Linq.Expressions.MethodCallExpression.Accept(ExpressionVisitor visitor)
   at System.Linq.Expressions.ExpressionVisitor.Visit(Expression node)
   at Microsoft.EntityFrameworkCore.Query.QueryCompilationContext.CreateQueryExecutor[TResult](Expression query)
   at Microsoft.EntityFrameworkCore.Storage.Database.CompileQuery[TResult](Expression query, Boolean async)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler.CompileQueryCore[TResult](IDatabase database, Expression query, IModel model, Boolean async)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler.<>c__DisplayClass9_0`1.<Execute>b__0()
   at Microsoft.EntityFrameworkCore.Query.Internal.CompiledQueryCache.GetOrAddQueryCore[TFunc](Object cacheKey, Func`1 compiler)
   at Microsoft.EntityFrameworkCore.Query.Internal.CompiledQueryCache.GetOrAddQuery[TResult](Object cacheKey, Func`1 compiler)
   at Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler.Execute[TResult](Expression query)
   at Microsoft.EntityFrameworkCore.Query.Internal.EntityQueryProvider.Execute[TResult](Expression expression)
   at Microsoft.EntityFrameworkCore.Query.Internal.EntityQueryable`1.GetEnumerator()
   at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
   at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
   at lambda_method(Closure , Object , Object[] )
   at Microsoft.Extensions.Internal.ObjectMethodExecutor.Execute(Object target, Object[] parameters)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ActionMethodExecutor.SyncObjectResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, Object controller, Object[] arguments)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeActionMethodAsync()
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeNextActionFilterAsync()
--- End of stack trace from previous location where exception was thrown ---
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Rethrow(ActionExecutedContextSealed context)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeInnerFilterAsync()
--- End of stack trace from previous location where exception was thrown ---
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeFilterPipelineAsync>g__Awaited|19_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, Object state, Boolean isCompleted)
   at Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
   at Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
   at Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequests[TContext](IHttpApplication`1 application)

回到我的问题,如何将Take() LINQ方法集成为LINQ-TO-T-SQL查询的一部分,以便所有查询都将通过EF Core进行并且所有查询操作都将在数据库中执行?

c# asp.net-mvc linq asp.net-core entity-framework-core
1个回答
0
投票

代码3:此版本的代码通过Take() LINQ方法成功返回了所需的结果数。但是,正在对已加载到客户端或内存中的数据/集合执行Take()。因此,此Take()执行LINQ-TO-Collections查询而不是LINQ-TO-T-SQL,并且不通过EF Core。

var q = from doctor in baseQuery

        let sp = (from ds in db.DoctorSpecialty
                  join s in db.Specialty on ds.SpecialtyID equals s.SpecialtyID
                  where ds.DoctorID == doctor.DoctorID
                  select new
                  {
                      s.SpecialtyID,
                      s.Specialty1
                  }).ToList()

        let clinics = (from c in db.Clinic
                  where c.DoctorID == doctor.DoctorID && c.Active == true

                  let schedule = (from sc in db.Schedule
                                  where sc.ClinicID == c.ClinicID
                                    && sc.DoctorID == doctor.DoctorID
                                    && DoctorDirectoryConstants.ValidScheduleNotes.Contains(sc.Notes)
                                  select sc).ToList()

                  select new
                  {
                      c.ClinicID,
                      c.Street,
                      c.ClinicName,
                      c.ContactNumber,
                      c.City,
                      c.Province,
                      c.HomeNumber,
                      c.MobileNumber,
                      c.WorkNumber,
                      c.Email,
                      Schedules = schedule,
                  }).ToList() 
        select new
        {
            Doctor = doctor,
            Specialties = sp,
            Clinics = clinics

        };

var rs = q.ToList();

rs = rs.AsEnumerable().Take(2).ToList();
© www.soinside.com 2019 - 2024. All rights reserved.