我有以下存储过程(每小时返回一台机器的事件数):
CREATE PROCEDURE sp_ReceivedEventsPerTimePerMachine
@dateFrom datetime,
@dateTo datetime,
@machineId uniqueidentifier
AS
IF DATEPART(MINUTE, @dateFrom) != 0 OR DATEPART(SECOND,@dateFrom)!= 0 OR DATEPART(MILLISECOND,@dateFrom)!= 0
RAISERROR ('dateFrom exceeds maximum precision. Only full hours are allowed.', 16, 1)
IF DATEPART(MINUTE, @dateTo) != 0 OR DATEPART(SECOND,@dateTo)!= 0 OR DATEPART(MILLISECOND,@dateTo)!= 0
RAISERROR ('dateTo exceeds maximum precision. Only full hours are allowed.', 16, 1)
IF (@@ERROR = 0)
SELECT
DATEADD(hh, DATEPART(hh, ReceiveDateTime), DATEADD(day, day(ReceiveDateTime) - 1, DATEADD(month, month(ReceiveDateTime) - 1, DATEADD(Year, year(ReceiveDateTime) - 1900, 0)))) AS DateTime,
COUNT(*) AS [NumberOfEvents]
FROM
ReceivedEvents
WHERE
ReceiveDateTime BETWEEN @dateFrom AND @dateTo
AND MachineId = @machineId
GROUP BY
DATEADD(hh, DATEPART(hh, ReceiveDateTime), DATEADD(day, day(ReceiveDateTime) - 1, DATEADD(month, month(ReceiveDateTime) - 1, DATEADD(Year, year(ReceiveDateTime) - 1900, 0))))
ORDER BY
DateTime
我使用EF6执行程序,这是我的C#代码:
var result = await Context.Database.SqlQuery<EventsPerDateTime>( "sp_ReceivedEventsPerTimePerMachine @dateFrom, @dateTo, @machineId",
new SqlParameter( "dateFrom", fromDateTime ), new SqlParameter( "dateTo", toDateTime ), new SqlParameter( "machineId", machine.MachineId ) )
.ToListAsync();
使用EF执行过程始终只返回一条记录,但该过程返回多个值。直接执行该过程(使用SQL Management Studio)返回多个记录。
如何使用EF获取select语句返回的所有记录?
修改
这是我的完整代码
以下是EventsPerDateTime
类:
public class EventsPerDateTime
{
public DateTime DateTime { get; set; }
public Int32 NumberOfEvents { get; set; }
}
用于抽象EF的服务
public class SqlService<TContext> : Disposable, ISqlService<TContext>
where TContext : DbContext, new()
{
private TContext _context;
private TContext Context
{
get
{
if ( _context == null )
{
Logger.Debug( "Request DbContext form database factory." );
_context = DatabaseFactory.GetDb();
}
return _context;
}
}
public IDatabaseFactory<TContext> DatabaseFactory { get; }
public SqlService( IDatabaseFactory<TContext> databaseFactory, ILoggerFactory loggerFactory )
: base( loggerFactory.CreateLogger( typeof (SqlService<TContext>) ) )
{
Logger.Trace( "Enter Ctor - Exit on next line." );
DatabaseFactory = databaseFactory;
}
protected override void Disposed()
{
if ( _context != null )
_context.Dispose();
}
public DbRawSqlQuery<TElement> SqlQuery<TElement>( String sql, params Object[] parameters )
{
return Context.Database.SqlQuery<TElement>( sql, parameters );
}
public DbRawSqlQuery SqlQuery( Type elementType, String sql, params Object[] parameters )
{
return Context.Database.SqlQuery( elementType, sql, parameters );
}
public Int32 ExecuteSqlCommand( String sql, params Object[] parameters )
{
return Context.Database.ExecuteSqlCommand( sql, parameters );
}
public Int32 ExecuteSqlCommand( TransactionalBehavior transactionalBehavior, String sql, params Object[] parameters )
{
return Context.Database.ExecuteSqlCommand( transactionalBehavior, sql, parameters );
}
public async Task<Int32> ExecuteSqlCommandAsync( String sql, params Object[] parameters )
{
return await Context.Database.ExecuteSqlCommandAsync( sql, parameters );
}
public async Task<Int32> ExecuteSqlCommandAsync( TransactionalBehavior transactionalBehavior,
String sql,
params Object[] parameters )
{
return await Context.Database.ExecuteSqlCommandAsync( transactionalBehavior, sql, parameters );
}
public async Task<Int32> ExecuteSqlCommandAsync( String sql,
CancellationToken cancellationToken,
params Object[] parameters )
{
return await Context.Database.ExecuteSqlCommandAsync( sql, cancellationToken, parameters );
}
public async Task<Int32> ExecuteSqlCommandAsync( TransactionalBehavior transactionalBehavior,
String sql,
CancellationToken cancellationToken,
params Object[] parameters )
{
return await Context.Database.ExecuteSqlCommandAsync( transactionalBehavior, sql, cancellationToken, parameters );
}
对服务的调用
var toDateTime = DateTime.Now.Date.AddHours( DateTime.Now.Hour );
var fromDateTime = toDateTime.Subtract( Parameters.ReceivedEventsOfLastHours.ToHours() );
var result =
await SqlService.SqlQuery<EventsPerDateTime>( "sp_ReceivedEventsPerTimePerMachine @dateFrom, @dateTo, @machineId",
new SqlParameter( "dateFrom", fromDateTime ),
new SqlParameter( "dateTo", toDateTime ),
new SqlParameter( "machineId", machine.MachineId ) )
.ToListAsync();
生成的SQL(使用SQL Server Profiler捕获):
exec sp_executesql
N'sp_ReceivedEventsPerTimePerMachine @dateFrom, @dateTo, @machineId',
N'@dateFrom datetime,@dateTo datetime,@machineId uniqueidentifier',
@dateFrom='2015-10-19 22:00:00',@dateTo='2015-10-21 22:00:00',@machineId='B0BDD062-0178-E511-9BD8-801F02F47041'