Hug*_*rio 14 c# asp.net-mvc entity-framework
我使用以下代码从存储过程中获取常规结果:
var paramUserId = new SqlParameter
{
ParameterName = "userId",
Value = userId
};
string query = string.Format("{0} {1}",
"SpSetFoo",
"@userId");
var results = context.Database.SqlQuery<FooModel>(query,
paramUserId);
result = results.ToList();
Run Code Online (Sandbox Code Playgroud)
同时我需要从另一个存储过程中检索多个结果集,根据这个文档,我发现它是可能的:http://msdn.microsoft.com/en-us/data/jj691402.aspx
但是,微软的例子是使用ADO.NET.如果没有使用EF的ADO.NET,不可能实现相同的结果吗?
谢谢
Wal*_*.K. 14
看到这个链接.这将首先适用于EF 6.0 Code.
http://www.khalidabuhakmeh.com/entity-framework-6-multiple-result-sets-with-stored-procedures
我基于上面的链接,我自己的扩展,C#6.0,添加参数和多个选择工作没有必要的程序.
public static class MultipleResultSets
{
#region Public Methods
public static MultipleResultSetWrapper MultipleResults(this DbContext db,string query,IEnumerable<SqlParameter> parameters=null) => new MultipleResultSetWrapper(db: db,query: query,parameters: parameters);
#endregion Public Methods
#region Public Classes
public class MultipleResultSetWrapper
{
#region Public Fields
public List<Func<DbDataReader,IEnumerable>> _resultSets;
#endregion Public Fields
#region Private Fields
private readonly IObjectContextAdapter _Adapter;
private readonly string _CommandText;
private readonly DbContext _db;
private readonly IEnumerable<SqlParameter> _parameters;
#endregion Private Fields
#region Public Constructors
public MultipleResultSetWrapper(DbContext db,string query,IEnumerable<SqlParameter> parameters = null)
{
_db = db;
_Adapter = db;
_CommandText = query;
_parameters = parameters;
_resultSets = new List<Func<DbDataReader,IEnumerable>>();
}
#endregion Public Constructors
#region Public Methods
public MultipleResultSetWrapper AddResult<TResult>()
{
_resultSets.Add(OneResult<TResult>);
return this;
}
public List<IEnumerable> Execute()
{
var results = new List<IEnumerable>();
using(var connection = _db.Database.Connection)
{
connection.Open();
var command = connection.CreateCommand();
command.CommandText = _CommandText;
if(_parameters?.Any() ?? false) { command.Parameters.AddRange(_parameters.ToArray()); }
using(var reader = command.ExecuteReader())
{
foreach(var resultSet in _resultSets)
{
results.Add(resultSet(reader));
}
}
return results;
}
}
#endregion Public Methods
#region Private Methods
private IEnumerable OneResult<TResult>(DbDataReader reader)
{
var result = _Adapter
.ObjectContext
.Translate<TResult>(reader)
.ToArray();
reader.NextResult();
return result;
}
#endregion Private Methods
}
#endregion Public Classes
}
Run Code Online (Sandbox Code Playgroud)
这是一个如何调用它的例子
var Policy = "123";
var Results= db
.MultipleResults($"EXEC GetPolicyInfo '{Policy}'")
.AddResult<Driver>()
.AddResult<Address>()
.AddResult<Phone>()
.AddResult<Email>()
.AddResult<Vehicle>()
.Execute();
var Output= new clsPolicyInfo
{
Drivers = Results[0] as Driver[],
Addresses = Results[1] as Address[],
Phones = Results[2] as Phone[],
Emails = Results[3] as Email[],
Vehicles = Results[4] as Vehicle[]
};
Run Code Online (Sandbox Code Playgroud)
这是一个古老的主题,但在这里添加评论以防万一有人需要它.我需要使用从不同数据库返回两个表的存储过程,然后处理存储到我们的应用程序数据库中的返回数据.提到标准文档并按照步骤但不喜欢它.首先是存在问题,代码暴露了一些不可靠性,从可维护性的角度来看这不是一个好主意.
那个专为处理SP而设计的Nuget包就会出现.看看CodeFirstStoredProcs.精美的包装,非常专注,完美地完成工作.这将返回存储过程的每个结果集的对象集合,然后可以按任何方式使用它们.它们是不同版本的EF(包括版本6)的良好且一致的支持.还要检查代码项目Code First Stored Procedures的说明.下载的源代码甚至还有一个PDF,解释了如何在详细步骤中使用它.
非常感谢作者aureolin.