我有一个SQL查询,其中我更新表记录,如果记录不存在,那么我创建一个新记录。
我的问题是,如何选择Inserted行或Updated行的Identity列?
我有以下查询:
UPDATE ProductsRoomsOrderLog
SET OrdersID = @OrdersID,
RoomID = @RoomID,
ProductID = @ProductID,
ProductDocumentDate = @ProductDocumentDate,
CreatedBy = @CreatedBy,
CreatedDate = @CreatedDate
WHERE ID = @ID
IF @@ROWCOUNT = 0
INSERT INTO ProductsRoomsOrderLog
(OrdersID,
RoomID,
ProductID,
ProductDocumentDate,
CreatedBy,
CreatedDate)
VALUES
(@OrdersID,
@RoomID,
@ProductID,
@ProductDocumentDate,
@CreatedBy,
@CreatedDate)
然后在C#中执行查询:
SqlCommand command = new SqlCommand(statement, connection);
try
{
connection.Open();
foreach (ProductsRoomsOrderLog logItem in log)
{
//Set Created Date
logItem.CreatedDate = createdDate;
command.Parameters.Clear();
if (logItem.ID == null)
{
command.Parameters.AddWithValue("@ID", DBNull.Value);
}
else
{
command.Parameters.AddWithValue("@ID", logItem.ID);
}
command.Parameters.AddWithValue("@OrdersID", logItem.OrdersID);
command.Parameters.AddWithValue("@RoomID", logItem.RoomID);
command.Parameters.AddWithValue("@ProductID", logItem.ProductID);
if (logItem.ProductDocumentDate == null)
{
command.Parameters.AddWithValue("@ProductDocumentDate", DBNull.Value);
}
else
{
command.Parameters.AddWithValue("@ProductDocumentDate", logItem.ProductDocumentDate);
}
command.Parameters.AddWithValue("@CreatedBy", logItem.CreatedBy);
command.Parameters.AddWithValue("@CreatedDate", logItem.CreatedDate);
command.ExecuteNonQuery();
//Get Identity column of inserted item
string selectIdentityStatement = "SELECT IDENT_CURRENT('ProductsRoomsOrderLog') FROM ProductsRoomsOrderLog";
SqlCommand selectIdentityCommand = new SqlCommand(selectIdentityStatement, connection);
logItem.ID = Convert.ToInt64(selectIdentityCommand.ExecuteScalar());
}
}
现在请注意,我有一个获取Identity列的select Query。不幸的是,这不能正常工作,因为它总是读取我表中最后一行的标识而不是当前有问题的行(无论是更新的行还是插入的行)。简单地说,只有在插入行时才更新行。
任何人都可以告诉我如何执行更新/插入查询并选择正确的行标识?老实说,如果我要插入行,我只关心检索标识列。
非常感谢,我非常感谢您花时间阅读本文。
答案 0 :(得分:1)
您必须在与INSERT相同的SQL命令中执行SELECT IDENT_CURRENT('ProductsRoomsOrderLog')
。
UPDATE ProductsRoomsOrderLog
SET OrdersID = @OrdersID,
RoomID = @RoomID,
ProductID = @ProductID,
ProductDocumentDate = @ProductDocumentDate,
CreatedBy = @CreatedBy,
CreatedDate = @CreatedDate
WHERE ID = @ID
IF @@ROWCOUNT = 0 BEGIN
INSERT INTO ProductsRoomsOrderLog
(OrdersID,
RoomID,
ProductID,
ProductDocumentDate,
CreatedBy,
CreatedDate)
VALUES
(@OrdersID,
@RoomID,
@ProductID,
@ProductDocumentDate,
@CreatedBy,
@CreatedDate)
SELECT IDENT_CURRENT('ProductsRoomsOrderLog')
END
然后使用ExecuteScalar
代替ExecuteNonQuery
来获取结果。
command.ExecuteNonQuery();
变为
object identity = command.ExecuteScalar();
if (identity is int)
logItem.ID = (int)identity;
答案 1 :(得分:1)
可能会将您的查询更改为
UPDATE ProductsRoomsOrderLog
SET OrdersID = @OrdersID,
RoomID = @RoomID,
ProductID = @ProductID,
ProductDocumentDate = @ProductDocumentDate,
CreatedBy = @CreatedBy,
CreatedDate = @CreatedDate
WHERE ID = @ID
IF @@ROWCOUNT = 0
BEGIN
INSERT INTO ProductsRoomsOrderLog
(OrdersID,
RoomID,
ProductID,
ProductDocumentDate,
CreatedBy,
CreatedDate)
VALUES
(@OrdersID,
@RoomID,
@ProductID,
@ProductDocumentDate,
@CreatedBy,
@CreatedDate);
SELECT IDENT_CURRENT('ProductsRoomsOrderLog') FROM ProductsRoomsOrderLog
END
ELSE
SELECT @ID
然后将其作为返回值的查询执行?
顺便说一句:您还可以查看SQL MERGE
statement,这使得INSERT / UPDATE逻辑更加直接。