Llame al procedimiento almacenado desde Dapper, que acepta la lista del tipo de tabla definido por el usuario.

Tengo un procedimiento almacenadoInsertCars que acepta la lista de tipo de tabla definida por el usuarioCarType.

CREATE TYPE dbo.CarType
AS TABLE
(
    CARID int null,
    CARNAME varchar(800) not null,
);

CREATE PROCEDURE dbo.InsertCars
    @Cars AS CarType READONLY
AS
-- RETURN COUNT OF INSERTED ROWS
END

Necesito llamar a este procedimiento almacenado de Dapper. Lo busqué en Google y encontré algunas soluciones.

 var param = new DynamicParameters(new{CARID= 66, CARNAME= "Volvo"});

 var result = con.Query("InsertCars", param, commandType: CommandType.StoredProcedure);

Pero me sale un error:

Procedimiento o función InsertCars tiene demasiados argumentos especificados

También procedimiento almacenadoInsertCars devuelve el recuento de filas insertadas; Necesito obtener este valor.

¿Dónde está la raíz del problema?

Mi problema también es que tengo autos en lista genérica.List<Car> Cars Y quiero pasar esta lista para guardar el procedimiento. ¿Existe forma elegante de cómo hacerlo?

public class Car
{
    public CarId { get; set; }
    public CarName { get; set; }
}

Gracias por ayudar

Editado

Encontré soluciones

¿Dapper admite los parámetros de valor de tabla de SQL 2008?

o

¿Dapper admite los parámetros de valor de tabla 2 de SQL 2008?

Así que trato de hacer propia clase de ayudante estúpido.

class CarDynamicParam : Dapper.SqlMapper.IDynamicParameters
{
    private Car car;

    public CarDynamicParam(Car car)
    {
        this.car = car;
    }

    public void AddParameters(IDbCommand command, SqlMapper.Identity identity)
    {
        var sqlCommand = (SqlCommand)command;

        sqlCommand.CommandType = CommandType.StoredProcedure;

        var carList = new List<Microsoft.SqlServer.Server.SqlDataRecord>();

        Microsoft.SqlServer.Server.SqlMetaData[] tvpDefinition =
                                                                {

                                                                    new Microsoft.SqlServer.Server.SqlMetaData("CARID", SqlDbType.Int),
                                                                    new Microsoft.SqlServer.Server.SqlMetaData("CARNAME", SqlDbType.NVarChar, 100),
                                                                };

        var rec = new Microsoft.SqlServer.Server.SqlDataRecord(tvpDefinition);
        rec.SetInt32(0, car.CarId);
        rec.SetString(1, car.CarName);

        carList.Add(rec);

        var p = sqlCommand.Parameters.Add("Cars", SqlDbType.Structured);
        p.Direction = ParameterDirection.Input;
        p.TypeName = "CarType";
        p.Value = carList;
    }
}

Utilizar

var result = con.Query("InsertCars", new CarDynamicParam(car), commandType: CommandType.StoredProcedure);

Me sale la excepción

Cuando utilice las API de asignación múltiple, asegúrese de establecer el parámetro splitOn si tiene claves distintas de Id.

StackTrace:

   at Dapper.SqlMapper.GetDynamicDeserializer(IDataRecord reader, Int32 startBound, Int32 length, Boolean returnNullIfFirstMissing) in c:\Dev\Dapper\Dapper\SqlMapper.cs:line 1308
   at Dapper.SqlMapper.GetDeserializer(Type type, IDataReader reader, Int32 startBound, Int32 length, Boolean returnNullIfFirstMissing) in c:\Dev\Dapper\Dapper\SqlMapper.cs:line 1141
   at Dapper.SqlMapper.<QueryInternal>d__d`1.MoveNext() in c:\Dev\Dapper\Dapper\SqlMapper.cs:line 819
   at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
   at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
   at Dapper.SqlMapper.Query[T](IDbConnection cnn, String sql, Object param, IDbTransaction transaction, Boolean buffered, Nullable`1 commandTimeout, Nullable`1 commandType) in c:\Dev\Dapper\Dapper\SqlMapper.cs:line 770
   at Dapper.SqlMapper.Query(IDbConnection cnn, String sql, Object param, IDbTransaction transaction, Boolean buffered, Nullable`1 commandTimeout, Nullable`1 commandType) in c:\Dev\Dapper\Dapper\SqlMapper.cs:line 715

¿Qué está mal?

FIJO:

Llamadacon.Execute en lugarcon.Query

Respuestas a la pregunta(3)

Su respuesta a la pregunta