3

谁能提供一些关于如何使用 NHibernate 实现时间状态表的提示/指针/链接?即,每个实体表都有start_dateend_date列,它们描述了认为该行有效的时间间隔。
当用户插入一个新实体时,start_date收到“现在”,而end_date将为空(或一个遥远的未来,我还没有决定)。
更新时,我想将 UPDATE 查询更改为以下内容:

  1. 更新此实体行的 end_date,以及
  2. 使用当前日期/时间和空 end_date 插入一个新行。

我尝试使用事件侦听器为 1 手动编写 UPDATE 查询,但似乎无法弄清楚如何为 2 实现新的 INSERT 查询。

这是正确的方法吗?还是我在这里完全偏离标准?

4

4 回答 4

2

实际上,如果我工作,我们有一个可行的解决方案,但它有效地杀死了 nhibernate 机制的一部分。

对于“时间实体”,NH 仅充当插入/选择引擎。删除和更新由另一个实用程序完成,其中 NH 的 ORM 部分派上用场。

如果您只有少数时间实体,您可能只使用 nhibernate,但准备编写自己的代码以确保状态关系有效。我们在第一次尝试中采用了这条路线,在时间实体的数量开始增加之后,该机制被有效地破坏了。

现在,插入不需要特殊工具,只需将值放在适当的日期时间属性中即可。我们使用过滤器实现选择(肯定检查 NH ref 的 16.1,因为它有一个示例,但条件不能使用 BETWEEN)虽然如果你这样做,你不得不修改 NH 源代码以将过滤器应用于各种选择. 检查我在http://savale.blogspot.com/2010/01/enabling-filters-on-mapped-entities.html上的帖子是否这样做。

如果您在映射上指定“where”子句(而不是过滤器),它也可能有效,但我还没有尝试或测试过它,我的理解是映射上的映射“where”不支持参数(至少不是正式的)。

正如我的旁注,一旦您阅读了 Richard Snodgrass 的时间数据库书籍http://www.cs.arizona.edu/~rts/publications.html ,使用自定义工具进行更新/删除的原因就会变得清晰

要直接回答您的问题,NULL _end 值和远在未来的值都可以使用(但更喜欢 NOT-NULL 解决方案,它会使您的查询更容易,因为您不必检查 ISNULL)。

对于更新,您可以有效地克隆原始实体,然后将原始实体的 _end 设置为现在,然后转到克隆并更改相关属性,将 _start 更改为现在,将 _end 更改为将来的值

于 2010-10-26T07:22:03.240 回答
1

我建议 Martin Fowler 的精彩时间叙事

于 2009-10-28T10:05:10.390 回答
0

虽然这篇文章已有几年历史,但这种模式似乎仍然有效。我还没有使用它,但我需要在当前项目中使用类似的解决方案,并将按照此处描述的方式对其进行建模。

于 2011-09-14T17:34:46.647 回答
0

我认为最好的方法是拥有类似 Java 地图的东西(对不起,我是一名 Java 程序员)并让 NHibernate 来映射它。该映射会将带有“开始”和“结束”字段的 Period 之类的东西映射到一个值。您可以编写一个 UserType 将 Period 映射到两个不同的数据库列

于 2010-10-25T21:05:58.213 回答