使用SQL Server 2008存档生产数据库插入/更新

时间:2012-04-05 19:07:29

标签: sql-server sql-server-2008 sql-server-2008-r2

我在第二个SQL Server实例中有一个生产数据库和一个存档数据库。

当我在生产数据库中插入或更新(NOT DELETE)数据时,我需要在存档数据库中插入或更新相同的数据。

这样做的好方法是什么?

由于

3 个答案:

答案 0 :(得分:1)

如果它们在同一个数据库实例中,假设它不是很多表,那么触发器将是微不足道的。

如果此大小增加,您可能希望查看SQL Server复制。微软花了很多时间和金钱去做正确的事。

答案 1 :(得分:0)

如果您正在考虑使用触发器,那么您可能需要考虑生产数据库的负载大小。如果它是非常密集的数据库,请考虑使用某些高可用性解决方案,例如复制或镜像或日志传送。根据您的需求,任何一种解决方案都可以为您提供服务。 同时,您应该考虑需要根据实施内容进行更改的“冷”恢复解决方案。

答案 2 :(得分:0)

复制也会复制您的删除。但是,不删除存档数据库中的删除可能会导致唯一索引上的问题,其中值在生产数据库中有效但在存档数据库中无效,因为其中已存在值。如果您的设计意味着这不是问题,那么生产表中的简单触发器将为您执行此操作:

CREATE TRIGGER TR_MyTable_ToArchive ON MyTable FOR INSERT, UPDATE AS
BEGIN
    SET ROW_COUNT OFF
    -- First inserts
    SET IDENTITY_INSERT ArchiveDB..MyTable ON -- Only if identity column is used
    INSERT INTO ArchiveDB..MyTable(MyTableKey, Col1, Col2, Col3, ...)
    SELECT MyTableKey, Col1, Col2, Col3, ...
    FROM inserted i LEFT JOIN deleted d ON i.MyTableKey = d.MyTableKey
    WHERE d.MyTableKey IS NULL
    SET IDENTITY_INSERT ArchiveDB..MyTable OFF -- Only if identity column is used

    -- then updates
    UPDATE t SET Col1 = i.col1, col2 = i.col2, col3 = i.col3, ...
    FROM ArchiveDB..MyTable t INNER JOIN inserted i ON t.MyTableKey = i.MyTableKey
        INNER JOIN deleted d ON i.MyTableKey = d.MyTableKey
END

这假定您的存档数据库与生产数据库位于同一服务器上。如果不是这种情况,则需要创建链接服务器条目,然后将ArchiveDB..MyTable替换为ArchiveServer.ArchiveDB..MyTable,其中ArchiveServer是链接服务器的名称。

如果您的生产数据库已经有很多负载,请记住这会使它加倍。为了避免这种情况,您可以在每个表中添加更新标志字段,并在数据库负载最小时(例如凌晨1点)运行计划任务。然后,您的触发器会将字段设置为I以进行插入,或将U设置为生产数据库中的更新,并且计划任务将执行然后更新或插入存档数据库,具体取决于此字段,然后在完成后将字段重置为NULL