数据库中某行中的每次数据更改都应将以前的行数据保存在某种历史记录中,以便用户可以回滚到上一行数据状态。这种方法有什么好的做法吗?尝试使用DataContract并对数据对象进行序列化和反序列化,但它对于复杂的对象变得不那么混乱。
所以更清楚:
我正在使用NHibernate进行数据访问,并希望避免使用数据库依赖(使用SQL Server 2005进行测试)
我的目的是提供数据历史记录,以便每次用户都可以回滚到以前的某些版本。
使用示例如下:
我希望我能给你有效的信息。
答案 0 :(得分:14)
主表更改时存储更改的表称为审计表。您可以通过多种方式执行此操作:
还要记住,一个事务可以同时修改多个记录,因此你应该使用完整的修改记录集,而不仅仅是最后一个记录(正如大多数人迟迟意识到的那样)。
在触发器执行完成之前,控件不会返回到调用程序。因此,您应该尽可能快地保持代码。
审核表的结构
您将拥有以下列:
Autonumber PK, TimeStamp, ActionType + All columns from your original table
我过去通过以下方式做到了这一点:
表格结构:
Autonumber PK, TimeStamp, ActionType, TableName, OriginalTableStructureColumns
此结构意味着您为每个保存的数据表创建一个审计表。数据保存和重建相当容易。我会推荐这种方法。
名称值对:
Autonumber PK, TimeStamp, ActionType, TableName, PKColumns, ColumnName, OldValue, NewValue
此结构将允许您保存任何表,但您必须为触发器中的每个列创建名称值对。这是非常通用的,但价格昂贵。您还需要编写一些视图以通过取消数据重新创建实际行。这变得乏味,通常不是遵循的方法。
答案 1 :(得分:5)
您可以使用触发器。 这是one示例。
AutoAudit is a SQL Server (2005, 2008)
Code-Gen utility that creates Audit
Trail Triggers with:
* Created, Modified, and RowVerwsion (incrementing INT) columns to table
* view to reconstruct deleted rows
* UDF to reconstruct Row History
* Schema Audit Trigger to track schema changes
* Re-code-gens triggers when Alter Table changes the table
答案 2 :(得分:5)
Microsoft已在SQL Server 2008中引入了新的审核功能。这篇文章描述了一些功能和设计目标,这些功能和设计目标可能对您选择的任何方法都有帮助。
答案 3 :(得分:2)
保存序列化数据最终总是变得混乱,你是正确的,远离那个。最好的办法是创建一个与主表具有相同列的并行“版本”表。
例如,如果您有一个名为“book”的表,其中包含列“id”,“name”,“author”,则可以添加名为“book_version”的表,其中包含列“id”,“name”,“作者“,”version_date“,”version_user“
每次在表“book”上插入或更新记录时,您的应用程序也会插入“book_version”。
根据您的数据库系统和数据库从应用程序访问的方式,您可以完全自动执行此操作(参见Doctr中的Versionable插件)
答案 4 :(得分:1)
一种方法是使用支持本地的数据库,如HBase。我通常不会建议“更改您的数据库服务器以获得这一功能”,但由于您没有在您的问题中指定数据库服务器,我认为您的意思是开放式服务器,并且服务器中的本机支持是这个功能的最佳实现之一。
答案 5 :(得分:0)
您使用的是什么数据库系统?如果您正在使用符合ACID(原子性,一致性,隔离,持久性)的数据库,那么您是否只能使用内置的回滚功能返回上一个事务?
答案 6 :(得分:0)
我使用NHibernate.Enverse
解决了这个问题对于那些有趣的人阅读: http://nhforge.org/blogs/nhibernate/archive/2010/07/05/nhibernate-auditing-v3-poor-man-s-envers.aspx