¿Hay alguna forma de usar Dapper.NET con procesos almacenados que devuelven múltiples conjuntos de resultados?
En mi caso, el primer conjunto de resultados es una sola fila con una sola columna; si es así, 0
la llamada fue exitosa, y el segundo conjunto de resultados contendrá las filas / columnas de datos reales. (y si no era cero, se produjo un error y no se proporcionará un segundo conjunto de resultados)
¿Alguna posibilidad de manejar esto con Dapper.NET? Hasta ahora, solo recuperaré ese single 0
, pero nada más.
Actualización: OK, funciona bien, siempre que el conjunto de resultados no. 2 es una sola entidad:
Dapper.SqlMapper.GridReader reader =
_conn.QueryMultiple("sprocname", dynParams,
commandType: CommandType.StoredProcedure);
int status = reader.Read<int>().FirstOrDefault();
MyEntityType resultObj = reader.Read<MyEntityType>().FirstOrDefault();
Ahora tengo otro requisito.
El mapeo múltiple de Dapper (dividiendo una sola fila devuelta desde SQL Server en dos entidades separadas) para ese segundo conjunto de resultados no parece ser compatible hasta el momento (al menos no parece haber una sobrecarga .Read<T>
que pueda manejar multi-mapeo).
¿Cómo puedo dividir esa fila en dos entidades?
Respuestas:
¿Has probado el
QueryMultiple
método? Dice que debería:Deberá agregar esta declaración using para habilitar QueryMultiple.
using Dapper; /* to add extended method QueryMultiple public static GridReader QueryMultiple(this IDbConnection cnn, string sql, object param = null, IDbTransaction transaction = null, int? commandTimeout = null, CommandType? commandType = null); */
fuente
QueryMultiple
admite la capacidad de tratar con múltiples conjuntos de resultados. La única restricción de diseño que agregamos fue la desactivación total del almacenamiento en búfer para el lector de cuadrícula. Esto significa que toda la API se está transmitiendo .En el caso más simple puedes usar:
var grid = connection.QueryMultiple("select 1 select 2"); grid.Read<int>().First().IsEqualTo(1); grid.Read<int>().First().IsEqualTo(2);
En el caso un poco más sofisticado, puedes hacer cosas locas como esta:
var p = new DynamicParameters(); p.Add("a", 11); p.Add("r", dbType: DbType.Int32, direction: ParameterDirection.ReturnValue); connection.Execute(@"create proc #spEcho @a int as begin select @a Id, 'ping' Name, 1 Id, 'pong1' Name select @a Id, 'ping' Name, 2 Id, 'pong2' Name return @a end"); var grid = connection.QueryMultiple("#spEcho", p, commandType: CommandType.StoredProcedure); var result1 = grid.Read<dynamic, dynamic, Tuple<dynamic, dynamic>>( (a, b) => Tuple.Create((object)a, (object)b)).ToList(); var result2 = grid.Read<dynamic, dynamic, Tuple<dynamic, dynamic>>( (a, b) => Tuple.Create((object)a, (object)b)).ToList(); ((int)(result1[0].Item1.Id)).IsEqualTo(11); ((int)(result1[0].Item2.Id)).IsEqualTo(1); ((int)(result2[0].Item1.Id)).IsEqualTo(11); ((int)(result2[0].Item2.Id)).IsEqualTo(2); p.Get<int>("r").IsEqualTo(11);
Deberá agregar esta declaración using para habilitar QueryMultiple.
using Dapper; /* to add extended method QueryMultiple public static GridReader QueryMultiple(this IDbConnection cnn, string sql, object param = null, IDbTransaction transaction = null, int? commandTimeout = null, CommandType? commandType = null); */
fuente
Conjunto de resultados múltiples.
Deberá agregar esta declaración using para habilitar QueryMultiple.
using Dapper; /* to add extended method QueryMultiple public static GridReader QueryMultiple(this IDbConnection cnn, string sql, object param = null, IDbTransaction transaction = null, int? commandTimeout = null, CommandType? commandType = null); */
Procedimiento almacenado:
CREATE PROCEDURE [dbo].[ProductSearch] @CategoryID as varchar(20), @SubCategoryID as varchar(20), @PageNumber as varchar(20) AS BEGIN SELECT * FROM ProductTbl SELECT * FROM ProductTbl END
fuente
.ToList()
? Veo que tanto usted como @Sam Saffron lo han hecho en sus ejemplos de código. ¿Tiene alguna implicación en el número de viajes de ida y vuelta o en la cantidad de datos devueltos?