Tôi có một thủ tục được lưu InsertCars
chấp nhận danh sách loại bảng do người dùng định nghĩa CarType
.Gọi thủ tục lưu sẵn từ người lập bản đồ chấp nhận danh sách loại bảng do người dùng định nghĩa
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
Tôi cần gọi thủ tục lưu trữ này từ Dapper. Tôi googled nó và tìm thấy một số giải pháp.
var param = new DynamicParameters(new{CARID= 66, CARNAME= "Volvo"});
var result = con.Query("InsertCars", param, commandType: CommandType.StoredProcedure);
Nhưng tôi nhận được một lỗi:
Procedure or function InsertCars has too many arguments specified
thủ tục Cũng lưu trữ InsertCars
trả về số lượng các hàng chèn; Tôi cần có giá trị này.
Gốc của sự cố ở đâu?
Vấn đề của tôi cũng là tôi có ô tô trong danh sách chung List<Car> Cars
và tôi muốn chuyển danh sách này để lưu trữ thủ tục. Nó tồn tại cách thanh lịch như thế nào để làm điều đó?
public class Car
{
public CarId { get; set; }
public CarName { get; set; }
}
Cảm ơn bạn đã giúp đỡ
EDITED
tôi tìm thấy giải pháp
Does Dapper support SQL 2008 Table-Valued Parameters?
hoặc
Does Dapper support SQL 2008 Table-Valued Parameters 2?
Vì vậy, tôi cố gắng làm ngu ngốc của riêng lớp helper
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;
}
}
Sử dụng
var result = con.Query("InsertCars", new CarDynamicParam(car), commandType: CommandType.StoredProcedure);
tôi nhận được ngoại lệ
When using the multi-mapping APIs ensure you set the splitOn param if you have keys other than 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
Có gì sai?
FIXED:
Gọi con.Execute
thay con.Query
đầu tiên tham số qua vấn đề ist thủ tục lưu trữ. Tôi nghĩ rằng số lượng và thứ tự là đúng. Tôi kiểm tra thủ tục của tôi thông qua MS SQL Studio và nó hoạt động tốt. Loại bảng do người dùng xác định chỉ có 2 cột, CARID và CARNAME. Trong DynamicParamater tôi chỉ thiết lập hai cột này. Vì vậy, tôi không hiểu nơi có thể là vấn đề? – imodin
@Wobe tôi đã đề cập đến cách hoàn chỉnh để thực hiện việc này. cho các tham số kiểu bảng tôi chuyển datatable như một tham số và không phải là một tham số dyamicparameter – Ehsan