2012-02-09 80 views
4

编辑时(比如在stackexchange项目中)保存所有帖子版本非常受欢迎,因为我们可以恢复旧版本。我想知道保存所有版本的最佳方法是什么。方法1:将所有版本存储在同一个表中,并为订单或活动版本添加一列。这会使桌子太长。如何在mysql数据库中保存帖子的所有版本

方法2:创建存档表以存储旧版本。

在这两种方法中,我想知道如何处理文章的主要标识符行ID。

+0

自引用外键字段。和表分区可能解决一些性能问题,也有一个大表但分区。 – 2012-02-09 13:03:08

回答

9

保存修订历史记录的“最佳”方式取决于您的具体目标/约束条件 - 而您未提及这些。

但在这里两个您建议的方法的一些想法:

  • 创建的帖子一个表,一个职位的历史,例如:

    create table posts (
        id int primary key, 
        userid int 
    ); 
    
    create table posthistory (
        postid int, 
        revisionid int, 
        content varchar(1000), 
        foreign key (postid) references posts(id), 
        primary key (postid, revisionid) 
    ); 
    

(显然会有是更多的列,外键等)。这是易于实现和易于理解(并容易让RDBMS保持参照完整性),但正如你所提到的可能导致posthistory有太多的行要足够快速地搜索。

请注意,postidposthistory(和posts的PK)中的外键。

  • 使用非规范化模式,其中所有最新修订都在一个表中,并且以前的修订位于单独的表中。这需要程序更多的逻辑,即when I add a new version, replace the post with the same id in the post table, and also add this to the revision table

(这可能是什么SE站点使用,基于SE Data Explorer数据转储。或者,也许不是,我不能告诉。)

对于这种方法,postid也是在posthistory表的外键,并在posts表的主键。

+2

+1我同意做到这一点的最佳方式是将“当前版本”存储在另一个“发布表”和“修订版”中,只有在需要时才能访问。 – Vyktor 2012-02-09 13:30:31

2

在我看来,一个有趣的方法是

  • 定义另一个表,例如posts_archive(它将包含posts表中的所有列+一个自增的主键+可选的日期......)
  • 通过在posts表上定义的后插入和更新后触发器来馈送此表。
2

如果表的大小是一个问题,那么第二个选项将是更好的选择。这样,活动版本可以从较小的表中快速返回,并且从较大的归档表恢复旧版本可能会花费更长的时间。也就是说,表的大小不应该是一个合理的数据库和索引的问题。

无论哪种方式,您都需要一个由多个表列组成的主键,而不仅仅是行ID。微不足道的答案是将包含创建每个修订版的时间的时间戳添加到密钥中,以便ID继续识别特定文章,ID和修订时间一起标识文章的特定修订版。

2

处理时态数据是已知的问题。

方法1只是简单地改变你的表格标识符:你最终将得到一个包含messageID, version, description, ...的表格,其主键为messageID, version。 修改数据是通过简单地添加一个增加版本的行来完成的。查询有点复杂。

方法2比较单调乏味,你最终会得到一个表格,其中有一个rowID,第二个表格与方法1中的表格完全相同。然后,​​在每次更新时,你都必须记得复制数据放入“备份表”中。

方法3:answser given by Matt

在我看来,方法1和3更好。该架构简化为1,但可以使用方法3为您的帖子提供未更改的数据。

相关问题