3

我需要解决以下问题:

我将在 SQL Server 2008 中创建一个每天都会更改的表。这是一个小表,最多可能有 5000 行,大约 5 个字段。

客户端将需要能够以在给定时间点的方式查看表中的所有数据。例如“告诉我两周前表格中的所有数据是什么样的”。

有人提到用http://autoaudit.codeplex.com/审计表可以解决这个问题。

我的问题:

  1. 有没有涉及简单审计的解决方案?
  2. 如果是这样,那么我将如何使用审计来解决这个问题?
  3. 是否已经存在针对此类挑战的不同解决方案,以便我不必重新发明轮子?
4

4 回答 4

2

有一个由触发器操纵的审计表。就像是:

create table YourAuditTable
(
    -- all of your source table's columns
    CreateDate datetime not null,
    DeleteDate datetime null
)
go

你的触发器看起来像这样:

create trigger AuditYourTable
on dbo.YourTable
after insert, update, delete
as

    if exists(select * from inserted)
    begin
        if exists(select * from deleted)
        begin
            -- this is for an update
            update YourAuditTable
            set DeleteDate = getdate()
            where YourIDCol in (select YourIDCol from deleted)
        end 

        -- this is just for an insert
        insert into YourAuditTable
        select *, getdate() as CreateDate
        from inserted
    end
    else
    begin
        -- this is just for a delete
        update YourAuditTable
        set DeleteDate = getdate()
        where YourIDCol in (select YourIDCol from deleted)
    end

go

这将允许您做的是查询您的审计表的时间点。换句话说,仅用于DATEDIFF确定是否在该给定时间点之前创建了行,并在其之后删除(或根本不删除)。

编辑

要查询您的审计表以获取时间点数据:

select *
from YourAuditTable
where CreateDate <= @PointInTimeDateTime
and
(
    DeleteDate is null or
    DeleteDate > @PointInTimeDateTime
)
于 2012-01-11T21:43:06.990 回答
1

您还可以将历史记录直接存储在表中。您添加一个 activedate 和一个 inactivedate 列。如果您不关心插入或更改的时间,请使用日期列而不是日期时间。

如果这是在现有系统上完成的,请更改表的名称。您编写一个仅显示当前活动记录的视图,并将其命名为旧表的名称(因此所有旧代码都不会中断)。

如果这是一个新系统,请使用上面提到的列创建表,并且仍然编写一个仅获取活动记录的视图。这将使您的开发人员能够始终如一地使用活动视图,因此当他们想要显示当前数据时,他们不会忘记过滤记录。

您将不得不更改通常执行更新记录过程的方式(我会在而不是触发器中执行此操作),以便在更新记录时,它会在当前记录中放入非活动日期并添加新记录。使用而不是触发器对删除执行相同操作以停用记录而不是删除它。如果这是一个新过程,您可以跳过触发器并简单地编写执行相同操作的更新,并在您想要删除时更新到提交的非活动日期。但是,我发现触发器在确保数据完整性方面更可靠。我个人会代替触发器,让开发人员在用户界面中编写正常的更新和删除。这将确保所有 chagnes 都得到正确处理,无论它们来自 GUI 还是来自 SSMS 中的临时更新。

然后,您编写一个带有日期参数的存储过程,以返回在日期输入上处于活动状态的数据(如果日期输入早于您开始执行此操作的数据,您可能需要一些特殊代码来处理),然后在 GUI 表单中使用它用户查看某个日期的数据。

于 2012-01-11T22:33:44.210 回答
1

您可以将您的表实现为“临时表”

这里发生的是唯一的“真实”表是保存历史的表。但是您也有一个索引视图,对于大多数意图,您可以以与原始表完全相同的方式处理它。由于它是一个索引视图,因此您可以添加任何额外的索引来提高性能。

插入/更新/删除性能有开销(但任何基于触发器的解决方案都会有开销)。

它确实很容易支持您要求的“时间点”访问(通过 UDF)。

如果您有任何想要添加或解释的内容,请告诉我 - 我在几个月前写了这篇文章(和后续文章),但随后对接下来要添加的内容失去了动力/想法。

于 2012-01-12T07:46:04.253 回答
-1

这是针对 MS SQL 的。(也只有在您需要显示特定日期的数据时才有效,如果您需要深入了解更精确的时间点,请使用审计表答案。)

鉴于表很小,最好使用 MS SQL 提供的 Snapshot 功能。

要制作数据库的快照:

CREATE DATABASE YourDB_Snapshot_DateStamp ON
( NAME = YourDB_Data, FILENAME = 
'C:\Program Files\Microsoft SQL Server\MSSQL10_50.MSSQLSERVER\MSSQL\Data\YourDB_Snapshot_DateStamp.ss' )
AS SNAPSHOT OF YourDB;
GO

请参阅此页面以供参考:http: //msdn.microsoft.com/en-us/library/ms175876.aspx

您可以根据需要制作任意数量的快照。所以我的建议是创建一个脚本或任务来创建每日快照并将日期附加到快照名称。这样,您将在服务器上看到所有快照。

需要注意的重要事项:快照是只读的。

于 2012-01-12T07:20:59.600 回答