如何表示当前状态或状态并维护数据/引用完整性?- 数据库设计

3
我有一个维护特定业务交易的表,我们称之为LOANS。每条记录在任何时候都可以具有多种“状态”,例如“正在还款/打开”,“违约”,“作废”或“已付款”。
记录的状态只能由应用程序用户执行的“事件”或操作更改(某些事件不会导致状态更改,例如付款修改记录但不更改状态)。在跟踪当前状态的同时,重要的是我们能够轻松地跟踪将交易置于此状态的“事件”。
我看到其他数据库的设置方式是,LOANS包含一个状态列,并使用字母(甚至是指向可能状态表的外键)来指定当前状态。然后,EVENTS表具有一个列,该列是对LOANSFK
这个解决方案可行,但我担心这可能会导致数据完整性丢失。换句话说,没有任何东西防止状态被设置为“违约”,而没有支持更改的EVENT。这将完全由应用程序确保永远不会发生(我认为这个解决方案中没有引用完整性)。
我的备选解决方案是放弃LOANS中的状态列,而是使用一个lastEvent列,它是对EVENTS的FK。然后,EVENTS表将维护“类型”事件,该事件将进而描述状态更改(例如,如果lastEvent是“payoff”类型,则自然状态为“paid”)。
我的问题是:
1.我应该担心数据完整性吗(这是一个常见的事情,因此可以这样做)?
2.我的提议解决方案是否可靠,或者是否有更好的解决方案?
3.我的解决方案中是否存在任何陷阱,我应该注意?
2个回答

3
  1. 只有您知道如果在此处没有参照完整性所带来的风险 - 但是通常情况下,设计数据库以便使用参照完整性是值得的。它可以减少错误,并增加未来开发人员理解模式的机会。

  2. 我会设计如下架构...

    贷款


    贷款_ID (PK)

    金额 ....

    事件


    事件_ID (PK)

    贷款_ID (FK)

    事件类型_ID (FK)

    日期

    状态_ID (fk)

    事件类型


    事件类型_ID (pk)

    描述

    状态


    状态_ID (pk)

    描述

要查找任何一个贷款的当前状态,您需要在该贷款的事件表中查找最新条目。要查看贷款状态更改的历史记录,则可以查询事件表。

当记录不更改状态的事件时,具有新事件的记录仅包含事件的当前状态-因此您可能会得到如下表格:

Event_id   Loan_ID Event_type_id    Date         status_id 
 ------------------------------------------------
 1               1           NEW   1 Jan 2011   NEW
 2               1       APPROVE   2 Jan 2011   NEW
 3               1       DEFAULT   1 Feb 2011   DEF
...

通过查找最新记录,您始终可以检索到当前状态。

这将大大降低错误风险 - 如果您的“事件”逻辑发生变化,并且某个事件确实改变了贷款的状态,则只需要在创建事件数据库中的记录的代码中更改此内容。您不必记得还要更改“贷款”记录。

至于性能-仅在确实需要时才进行优化 - 在调整良好的数据库上,连接和max应该不会成为问题。

您可以通过创建一个表来映射有效的状态转换及其关联事件来完善模型;根据您的数据库,您可以通过触发器强制执行此操作。

我认为这比“最后一个事件”外键更好,因为它是冗余的-根据定义,最后一个事件是该贷款的MAX(date)记录。


有些事件不会改变状态,这是我选择不仅仅查看最后一个事件的原因之一(但也许我可以推断出那些不改变状态的事件需要一个初始状态)。另一个原因是我认为将其存储在lastEvent中可能比每次调用MAX(date)更快地获取特定状态的所有项目(这种调用将经常发生)。 - LittleTreeX

0

我认为你对完整性的关注是有道理的。你已经指定了一个业务规则,实际上状态不是可写属性,而是从事件中推断出来的。

我会根据你的事件数据创建一个可计算列

我只能猜测你的数据库实现,所以另一种选择是触发器更新列,但是你如何确保它是只读的呢?(可能需要使用锁/权限)


我正在使用 SQL SERVER 2005,为了明确问题而添加。 - LittleTreeX
计算列在2005年可用,查看我发送的链接顶部的“其他版本”。 - jenson-button-event

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接