【问题标题】:Stored Procedure returns int value rather than result set in Entity Framework存储过程返回 int 值而不是实体框架中的结果集
【发布时间】:2015-12-10 07:34:25
【问题描述】:

我有这个存储过程

create procedure [dbo].[sp_GetAllLesiureActivitiesNew]
    (@ActivityLeaderID int = null)
as 
begin
    declare @TempLeisureActivites TABLE
        ([ActivityPlan_ID] [int]  NULL,
         [ActivityRecurrence_ID] [int] NULL,
         [ActivityName] [nvarchar](50) NULL,
         [Activity] [nvarchar](max) NULL,   
         [IsResponse] [bit] NULL,
         [IsLOI] [bit] NULL,
         [clientcount] [int] NULL,  
         [Location] [nvarchar](max) NULL,
         [StartDateTime] [datetime] NULL,
         [EndDatetime] [datetime] NULL)

    insert into @TempLeisureActivites
        select distinct 
            ap.ActivityPlan_ID, ap.ActivityRecurrence_ID, 
            ap.ActivityName, orgla.Activity, orgla.IsResponse,
            orgla.IsLOI,
            (select count(distinct cc.ID ) from Client cc join Activity_Clients acc on cc.ID=acc.Client_ID join ActivityPlan app on acc.ActivityRecurrence_ID=app.ActivityRecurrence_ID where app.ActivityRecurrence_ID=ap.ActivityRecurrence_ID  and cc.Status=1) as clientcount,l.Location,ap.StartDateTime,ap.EndDatetime 
from ActivityPlan ap
left outer join Location l on ap.ActivityLocationID =l.ID left join Activity_Clients ac on ap.ActivityRecurrence_ID=ac.ActivityRecurrence_ID 
left outer join Client c on ac.Client_ID=c.ID
left outer join LeisureActivity orgla on ap.ActivityType=orgla.ID 
where ap.ActivityLeaderID in(0,@ActivityLeaderID) and c.[Status]=1

    if(@ActivityLeaderID is not null and @ActivityLeaderID>0)
    begin


declare @Activities nvarchar(max)
declare @Locations nvarchar(max)
declare @CISelection nvarchar(50)
declare @IsAllLocs bit

declare @TempRecurID int
declare @TempAPID int

--BEGIN TRANSACTION T1
--BEGIN TRY

 declare @RecurIDsCursor CURSOR
declare @RecurIDsRowsCount int

 --print 'Before cursor logic starts'
set @RecurIDsCursor=CURSOR STATIC FOR
select ActivityPlan_ID,ActivityRecurrence_ID from @TempLeisureActivites

OPEN @RecurIDsCursor
set @RecurIDsRowsCount=(SELECT @@CURSOR_ROWS)

--print 'cursor rows count:'+cast(@RecurIDsRowsCount as nvarchar)

FETCH NEXT
FROM @RecurIDsCursor INTO @TempAPID,@TempRecurID

WHILE @RecurIDsRowsCount>0
BEGIN

--select @Activities=NULL,@Locations=NULL
--print 'looping started...'
select @Activities='',@Locations=''

select @CISelection=NULL,@IsAllLocs=0

--print 'Activity Plan ID'+cast(@TempAPID as nvarchar)+',Recur ID:'+ cast(@TempRecurID as nvarchar)

select @CISelection=[CommonInterestsSelection] from [dbo].[ActivityPlan] where ActivityPlan_ID=@TempAPID and [ActivityRecurrence_ID]=@TempRecurID


--print 'CI Selection:'+@CISelection

if(@CISelection='Specific')
begin
select @Activities+=(
case when la.Activity is not null then 
 ISNULL(la.Activity,'')+',' end) from [dbo].[ActivityPlan_Filters] apf
left outer join [dbo].[LeisureActivity] la on la.ID=apf.FilterID 
where [ActivityRecurrence_ID]=@TempRecurID and apf.FilterType='Common_Interests'

if(LEN(@Activities)>0)
begin
select @Activities=LEFT(@Activities, LEN(@Activities) - 1)
end
end
else if(@CISelection='Top')
begin
select @Activities=[CommonInterestValue] from [dbo].[ActivityPlan] where ActivityPlan_ID=@TempAPID and [ActivityRecurrence_ID]=@TempRecurID
end
else if(@CISelection='NA')
begin
select @Activities='ALL'
end

--print 'Activities:'+@Activities
select @IsAllLocs=[IsAllLocations] from [dbo].[ActivityPlan] where ActivityPlan_ID=@TempAPID and [ActivityRecurrence_ID]=@TempRecurID
if(@IsAllLocs=1)
begin
select @Locations='ALL'
end
else if(@IsAllLocs=0)
begin
select @Locations+=(
case when loc.Location is not null then 
 ISNULL(loc.Location,'')+',' end) from [dbo].[ActivityPlan_Filters] apf
left outer join [dbo].[Location] loc on loc.ID=apf.FilterID 
where [ActivityRecurrence_ID]=@TempRecurID and apf.FilterType='Locations'

if(LEN(@Locations)>0)
begin
select @Locations=LEFT(@Locations, LEN(@Locations) - 1)
end
end

--print 'Locations:'+@Locations

--print 'before updation'
update @TempLeisureActivites
set Activity=@Activities,Location=@Locations
where ActivityPlan_ID=@TempAPID and ActivityRecurrence_ID=@TempRecurID

--print 'after updation'

FETCH NEXT
FROM @RecurIDsCursor INTO @TempAPID,@TempRecurID

SET @RecurIDsRowsCount=@RecurIDsRowsCount-1
END
CLOSE @RecurIDsCursor
DEALLOCATE @RecurIDsCursor


end
select * from @TempLeisureActivites
end

它在 SQL Server Management Studio 中执行时返回结果集,但在使用实体框架的 Asp.net MVC 中它返回一个整数而不是如下所示的结果集。

  public virtual int sp_GetAllLesiureActivitiesNew(Nullable<int> activityLeaderID)
        {
            var activityLeaderIDParameter = activityLeaderID.HasValue ?
                new ObjectParameter("ActivityLeaderID", activityLeaderID) :
                new ObjectParameter("ActivityLeaderID", typeof(int));

            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction("sp_GetAllLesiureActivitiesNew", activityLeaderIDParameter);
        }

我找到了一篇文章,但它对我没有帮助 (Stored procedure returns int instead of result set)。 我该如何解决我的问题?

【问题讨论】:

  • 存储过程的返回值是一个INT,指定受操作影响的行数(如INSERTDELETEUPDATE)。对于不使用任何这些操作的存储过程,存储过程的返回值定义为 -1。要从存储过程中获取结果集,请尝试使用 .ExecuteStoreQuery() 方法而不是 ExecuteFunction
  • @marc_s 上面的存储过程在 Sql Server 管理工作室中执行时返回行。它在 sql server 中返回正确的表结果。但在实体框架中它返回整数而不是结果集。
  • 是的 - 我知道 - 你说过 - 我试图告诉你使用 ExecuteStoreQuery() 而不是 ExecuteFunction 能够得到那些行 .....
  • 旁注:您应该为您的存储过程使用sp_ 前缀。微软有reserved that prefix for its own use (see Naming Stored Procedures),你确实会在未来某个时候冒着名称冲突的风险。 It's also bad for your stored procedure performance。最好只是简单地避免 sp_ 并使用其他东西作为前缀 - 或者根本不使用前缀!

标签: entity-framework sql-server-2008


【解决方案1】:

ExecuteFunction() 方法以整数形式返回受影响的行数。

如果您希望它返回ObjectResult&lt;YourEntityType&gt;。 改成:

return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction<YourEntityType>("sp_GetAllLesiureActivitiesNew", activityLeaderIDParameter);

但我认为现在更好的做法是:

Dbcontext.Database.SqlQuery<YourEntityType>("storedProcedureName",params);

Here 是一篇展示示例的文章。

【讨论】:

  • 在 DbContext.cs 中返回整数,如下所示 public virtual int sp_GetAllLesiureActivitiesNew(Nullable activityLeaderID){}
  • 如果要返回 ObjectResult,必须知道 EntityType。看我的更新!否则它只会将受影响的行数作为整数返回。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-04-08
  • 1970-01-01
  • 2012-05-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多