Search 通过对象事务存储和搜索的最佳方式是什么?

Search 通过对象事务存储和搜索的最佳方式是什么?,search,transactions,oop,storage,Search,Transactions,Oop,Storage,我们有一个相当大的面向对象应用程序。每当应用程序中的对象发生更改时,对象更改都会保存回数据库。然而,这已变得不太理想 目前,事务存储为一个事务和一组事务 事务表中有用于who、what、when、why、foreignKey和foreignTable的字段。前四个是不言自明的。ForeignKey和foreignTable用于确定更改了哪个对象 TransactionLI具有时间戳、键、val、oldVal和transactionID。这基本上是一个键/值/旧值存储系统 问题是这两个表用于应用程

我们有一个相当大的面向对象应用程序。每当应用程序中的对象发生更改时,对象更改都会保存回数据库。然而,这已变得不太理想

目前,事务存储为一个事务和一组事务

事务表中有用于who、what、when、why、foreignKey和foreignTable的字段。前四个是不言自明的。ForeignKey和foreignTable用于确定更改了哪个对象

TransactionLI具有时间戳、键、val、oldVal和transactionID。这基本上是一个键/值/旧值存储系统

问题是这两个表用于应用程序中的每个对象,所以它们现在是相当大的表。用它们做任何事情都很慢。索引只能起到这么大的作用

所以我们正在考虑其他方法来做类似的事情。到目前为止,我们已经考虑过的事情: -用时间戳之类的东西来划分这些表。 -对两个表进行非规范化并将它们合并为一个表。 -以上两者的结合。 -在更改后序列化每个对象并将其存储在subversion中。 -可能是别的,但我现在想不起来

整个问题是,我们希望有某种机制来正确地存储和搜索事务性数据。是的,您可以将其强制输入到关系数据库中,但实际上,它是事务数据,应该相应地存储


其他人都在干什么?

我从来没有找到解决这类问题的好办法。您可以尝试的一些方法是,如果您的DB支持分区(或者即使不支持分区,您也可以自己实现相同的概念),但可以按对象类型分区此日志表,然后可以按日期/时间或对象ID进一步分区(如果您的ID是数字,则可以很好地工作,但不确定guid如何分区)

这将有助于保持表的大小,并将对象的单个实例的所有相关事务都保留在其自身

您可以探索的一个想法是,您可以将数据存储为blob(文本或二进制),而不是将每个字段存储在名称-值对表中。例如,将对象序列化为Xml并将其存储在字段中

<> P>这是因为当你的对象发生变化时,你必须考虑这是如何影响所有历史数据的,如果你使用XML,那么有简单的方法来更新历史XML结构,如果你使用二进制的方式,但是你必须更加努力。 我已经成功地将一个相当复杂的对象模型存储为一个blob,该模型具有大量的相互关系(在.net中,xml序列化程序没有处理对象之间的关系)。我可以很容易地看到自己在存储二进制数据。将其存储为二进制数据的一个巨大缺点是,要访问它,必须使用Xml将其从数据库中取出,如果您使用MSSQL之类的现代数据库,则可以访问数据

最后一种方法是拆分这两种模式,您可以定义一个不同的模式(我假设一次更改多个属性),例如,想象一下存储以下xml:

<objectDiff>
<field name="firstName" newValue="Josh" oldValue="joshua"/>
<field name="lastName" newValue="Box" oldValue="boxer"/>
</objectDiff>

这将有助于减少行数,如果您使用MSSQL,您可以定义XML模式,并获得一些有关对象的丰富查询功能。您仍然可以对表进行分区


Josh

根据特定应用程序的特点,另一种方法是将实体本身的修订以及每个修订的人、内容、原因和时间保存在各自的表中。who、what和when仍然可以是外键


尽管我会非常小心地使用这种方法,因为这只适用于每个实体/实体类型的更改量相对较小的应用程序

如果查询数据很重要,如果您有企业版SQL Server,我会在SQL Server 2005及更高版本中使用真正的分区。在本月内,我们有数百万行按年到日进行分区—您可以根据应用程序的要求进行细化,最多可以有1000个分区

或者,如果您使用的是SQL 2008,则可以查看筛选的索引

这些解决方案将使您能够保留现有的简化结构,同时提供查询该数据所需的性能


显然,应该考虑拆分/归档旧的更改

我们采取了以下方法:-

  • 所有对象都是序列化的(使用标准的XMLSeriliser),但是我们已经用序列化属性修饰了我们的类,因此生成的XML要小得多(例如,将元素存储为属性并在字段名上删除元音)。如果需要,可以进一步压缩XML

  • 通过SQL视图访问对象存储库。该视图面向许多结构相同但表名附加了GUID的表。当上一个表达到临界质量(预先确定的行数)时,将生成一个新表

  • 我们每晚运行一个归档例程,生成新表并相应地修改视图,以便调用的应用程序不会看到任何差异

  • 最后,作为夜间例行程序的一部分,我们将不再需要的任何旧对象实例归档到磁盘(然后归档到磁带)


  • 你在使用什么数据库?您可能希望在SQL 2008中调查SQL更改跟踪。它不会跟踪对象,但会跟踪数据更改并对其进行版本设置。