我有以下触发器:
ALTER TRIGGER [Staging].[tr_UriData_ForInsert]
ON [Staging].[UriData]
FOR INSERT
AS
BEGIN
DECLARE @_Serial NVARCHAR(50)
DECLARE @_Count AS INT
IF @@ROWCOUNT = 0
RETURN
SET NOCOUNT ON;
IF EXISTS(SELECT * FROM inserted)
BEGIN
SELECT @_Count = COUNT(Id) FROM inserted
SELECT @_Serial = SerialNumber FROM inserted
INSERT INTO [Staging].[DataLog]
VALUES (CURRENT_TIMESTAMP, @_Serial + ': Data Insert --> Rows inserted: ' + @_Count, 'New data has been received')
END
END
表一次接收多行。我希望能够在日志表中添加一行以告诉我插入已发生。
插入一行时效果很好,但是如果插入多行,触发器不会触发。我在这里还阅读了其他文章,很明显,您不应该使用ROW_NUMBER()
。
总结:当另一个表UriData中发生多行插入时,我想更新我的日志表。
使用以下命令从C#插入数据:
using (var sqlBulk = new SqlBulkCopy(conn, SqlBulkCopyOptions.Default, transaction))
{
sqlBulk.DestinationTableName = tableName;
try
{
sqlBulk.WriteToServer(dt);
}
catch(SqlException sqlEx)
{
transaction.Rollback();
var msg = sqlEx.Message;
return false;
}
finally {
transaction.Commit();
conn.Close();
}
}
我不想知道要插入的内容,但是什么时候发生,所以我可以运行一组SPROCS来清理和旋转数据。
TIA
答案 0 :(得分:6)
问题在于您的触发器假定将仅更新一行。标量变量只能有1个值。因此,例如,语句SELECT @_Serial = SerialNumber FROM inserted
将@_Serial
设置为对象inserted
返回的最后一个值。
按数据集的形式处理数据。这未经测试,但是,我怀疑这会为您提供所需的结果:
ALTER TRIGGER [Staging].[tr_UriData_ForInsert]
ON [Staging].[UriData]
FOR INSERT
AS
BEGIN
--No need for a ROWCOUNT. If there are no rows, then nothing was inserted, and this trigger won't happen.
INSERT INTO [Staging].[DataLog] ({COLUMNS LIST})
SELECT CURRENT_TIMESTAMP,
SerialNumber + ': Data Insert --> Rows inserted: ' +
CONVERT(varchar(10),COUNT(SerialNumber) OVER (PARTITION BY SerialNumber)), --COUNT returns an INT, so this statement would have failed with a conversion error too
'New data has been received'
FROM inserted;
END
请注意我的评论或大括号({}
)中的部分。
编辑:此后删除答案的肖恩(Sean)使用了GROUP BY
。我复制了您使用的确切方法,但是,GROUP BY
可能是您想要的子句,而不是OVER
。
答案 1 :(得分:0)
因此,在经过大量的研究和争论之后,我的托管公司告诉我,他们禁用了任何形式的散装插入物,而不必费心通知客户。