从触发器的插入和删除表中动态获取列值

时间:2019-06-12 12:53:27

标签: sql sql-server sql-server-2012 triggers database-trigger

以下是要求和采取的方法/设计 需求: 当且仅当列的值已更改时,才需要插入“历史记录”表以更新表的任何列。 需要为SQL列名称插入旧值,新值和用户友好列名称(向用户显示历史记录) 设计/方法:

  1. 更新列。 遍历每一列

a。动态创建查询以从插入和删除的表中获取列值

b。从映射表中获取该列的用户友好列名

c。插入历史记录表

问题:Exec sp_executesql抛出错误

使用下面的代码中提到的Exec sp_executesql来获取值。但这不起作用

CREATE TRIGGER dbo.InsertArchiveInfoOnUpdate 
ON  dbo.A
AFTER UPDATE
AS 
BEGIN
IF OBJECT_ID('tempdb..#COLUMNVALUES') IS NOT NULL
DROP TABLE #COLUMNVALUES
CREATE TABLE dbo.#COLUMNVALUES
(
ColumnName VARCHAR(50),
Value varchar(MAX) 
)
SELECT * INTO #INSERTEDTABLE FROM INSERTED
SELECT * INTO #DELETEDTABLE FROM DELETED
DECLARE @Columns_Updated VARCHAR(max)
DECLARE @ParmDefinition nvarchar(500); 
DECLARE @ColumNameVariable VARCHAR(MAX);
DECLARE @COLUMNNAMEVALUEOUTPUT VARCHAR(max);
DECLARE @COLUMNNAMEVALUE VARCHAR(max); 
DECLARE @COLUMN VARCHAR(MAX)
SET NOCOUNT ON;
DECLARE @idTable      INT
SELECT  @idTable = T.id 
FROM    sysobjects P JOIN sysobjects T ON P.parent_obj = T.id 
WHERE   P.id = @@procid
SELECT  @Columns_Updated = ISNULL(@Columns_Updated + ', ', '') + name 
FROM    syscolumns 
WHERE   id = @idTable   
AND     CONVERT(VARBINARY,REVERSE(COLUMNS_UPDATED())) & POWER(CONVERT(BIGINT, 2), colorder - 1) > 0
DECLARE @COLUMNNAME VARCHAR(max)
DECLARE @OldColumnValue VARCHAR(MAX)
DECLARE @NewColumnValue VARCHAR(MAX)
DECLARE @UserFriendlyName VARCHAR(MAX)
DECLARE @OldColumnValueQuery VARCHAR(MAX)
DECLARE @NewColumnValueQuery VARCHAR(MAX)
DECLARE @MappingValueQuery VARCHAR(MAX)
DECLARE @InsertArchiveInfoValues VARCHAR(MAX)
--This table valued function will return us the column names which were updated
DECLARE UPDATED_COLUMNS CURSOR FOR select value from dbo.fn_split_string_to_column(@Columns_Updated,',')
OPEN UPDATED_COLUMNS 
FETCH NEXT FROM UPDATED_COLUMNS INTO @COLUMNNAME
WHILE @@FETCH_STATUS = 0  
BEGIN  
BEGIN TRY
print 1
SET @OldColumnValueQuery ='SELECT @OldColumnValue=@COLUMN FROM #DELETEDTABLE'
SET @NewColumnValueQuery ='SELECT @NewColumnValue=' +@COLUMNNAME+' FROM #INSERTEDTABLE'
SET @MappingValueQuery ='SELECT @UserFriendlyName=LABEL_NAME FROM dbo.TABLE_MAPPING WHERE COLUMN_NAME='''+@COLUMNNAME+''''
SET @ParmDefinition = N'@COLUMN VARCHAR(MAX),@OldColumnValue VARCHAR(max) OUTPUT';  
EXECUTE sp_executesql @OldColumnValueQuery, @ParmDefinition, @COLUMN = @COLUMNNAME,@OldColumnValue=@COLUMNNAMEVALUE OUTPUT;          select @COLUMNNAMEVALUE     
--EXEC @NewColumnValueQuery
--EXEC @MappingValueQuery   
END TRY
BEGIN CATCH
INSERT INTO COLUMNNAME VALUES(ERROR_MESSAGE())
END CATCH
FETCH NEXT FROM UPDATED_COLUMNS INTO @COLUMNNAME
END 

CLOSE UPDATED_COLUMNS  
DEALLOCATE UPDATED_COLUMNS 
END
IF OBJECT_ID('tempdb..#COLUMNVALUES') IS NOT NULL
DROP TABLE #COLUMNVALUES
GO

需要从插入和删除的表中获取旧值和新值。

0 个答案:

没有答案