通常,捕获历史记录的最佳解决方案是创建一个触发器,该触发器在更新到历史记录表时获取记录的快照但是:
1。)我的表包含60列,但我想只捕获10个列的历史记录。
2。)来自数据源的数据带有提交日期,但未在目标表中捕获。根据源发送的提交日期而不是基于当前的sysdate来捕获历史记录。
3.)我们可以控制选择,更新过程。
建议的解决方案:
我们创建了一个函数,如下所示
In(Primary Key, Submit_Date, Column_Name, Old Value, New Value)
PRAGMA AUTONOMOUS_TRANSACTION;
Fetch max(Submit_date) From History using PK;
If max_Submit_date is Null:
Insert in History using PK, 01-01-1700 as Submit date, Column Name, Old_Value;
Insert into History using PK & Submit_date & new Value;
Elsif max_Submit_date = Submit_date
Update History using PK & Submit_date with new Value;
Elsif max_Submit_date < Submit_date
Insert into History using PK & Submit_date & new Value;
End if;
commit;
在选择要更新的数据时,我们添加了
select .... ,
DECODE(T.Column_VALUE_1,S.Column_VALUE_1,NULL,Function(PK,'COLUMN_NAME_1', S.Submit_Date, T.Column_VALUE_1, S.Column_VALUE_1)) XYZ,
DECODE(T.Column_VALUE_2,S.Column_VALUE_2,NULL,Function(PK,'COLUMN_NAME_2', S.Submit_Date, T.Column_VALUE_2, S.Column_VALUE_2)) XYZ,
From Source_Table S Join Target Table T Where ...
我可以看到解决方案不理想或不高效。请告知是否可以通过其他方式满足要求。
答案 0 :(得分:0)
一种解决方案可能是使用MERGE INTO
语句立即对所有记录执行此操作。由于您的submit_date属于insert
并且也是比较,因此避免冲突的理想解决方案是在version
表中包含History
列,初始版本包含1和2,3, 4 ..等等后续版本。
而不是与解码和调用函数进行比较,您可以在where子句条件中排除所有此类记录。
MERGE INTO HISTORY h USING
(
with m(pk,max_Submit_date) AS
( select pk,submit_date,version
FROM HISTORY o where
version IN ( select MAX(version) max_version
FROM HISTORY i where i.pk = o.pk ) ,
select .... PK,
CASE WHEN m.max_Submit_date is Null
THEN 01-01-1700
WHEN m.max_Submit_date <= s.Submit_date THEN
s.Submit_date
END as Submit_date,
decode( m.max_Submit_date,NULL,T.Column_VALUE_1, S.Column_VALUE_1)
decode( m.max_Submit_date,NULL,T.Column_VALUE_2, S.Column_VALUE_2)
..
CASE WHEN m.max_Submit_date is Null
THEN 1
WHEN m.max_Submit_date <= s.Submit_date
THEN m.max_version + 1 new_version
ELSE
m.max_version
END version
From Source_Table S Join Target Table T
JOIN m ON m.pk = s.pk
Where ..
( T.Column_VALUE_1 != S.Column_VALUE_1 ) OR
( T.Column_VALUE_2 != S.Column_VALUE_2 ) OR
..
..
) cur
ON ( cur.pk = h.pk and h.version = cur.version )
WHEN MATCHED THEN
Update SET h.Submit_date = cur.Submit_date,
h.Column_VALUE_1 = s.Column_VALUE_1,
h.Column_VALUE_2 = s.Column_VALUE_2
..
WHEN NOT MATCHED THEN INSERT
INSERT (PK,submit_date,column_1,..) VALUES (..);