用于存储类似银行的帐户和交易的数据库结构

时间:2012-06-24 15:13:05

标签: mysql database-design database-schema banking

我们正在为自己的商店添加类似银行的子系统。

我们已经拥有客户,因此每个客户都会获得一种账户,并且可以进行某种交易(添加到账户或从中扣除)。

因此,我们至少需要帐户实体,交易,然后操作必须重新计算总体余额。

您如何构建数据库来处理此问题?

是否有任何我可以使用的标准银行系统?

顺便说一句,我们在mysql上,但也会看一些nosql解决方案以提升性能。

2 个答案:

答案 0 :(得分:3)

我认为你不需要NoSQL来提高速度,因为它不太可能需要太多/任何并行性,也不确定你可能需要非面向架构。除非你开始涉及数百万客户和数亿交易的分析的复杂业务需求,例如盈利能力,甚至那时候你可能不会在你的交易模式中运行这种类型的数据仓库式问题如果它变得那么大,那就是第一个。

在关系设计中,我倾向于避免任何需要平衡重新计算的设计,因为那样你最终会得到平衡修复程序等。通过适当的索引和简单的设计,你可以对事务做一个简单的SUM(积极和消极)以获得平衡。在交易中具有良好的一致符号约定(没有关于是否添加或减去的模糊 - 总是添加值)和适当的约束(具有有限数量的交易类型,您可以使用约束条件指定所有存款均为正数且所有提取均为负数你可以让数据库确保没有负面存款等异常现象。

即使您想以某种方式缓存余额,您仍然可以依赖于在事务表上使用触发器增强的这种简单机制来更新帐户汇总表。

我不喜欢把这些任何东西放在数据库之外的中间层。您的基本会计应该相当简单,以便可以在数据库引擎内快速处理,以便执行查询的任何人或任何部分应用程序将获得相同的答案,而不涉及任何客户端代码逻辑。因此,数据库使用约束,触发器和存储过程的组合,确保在略高于参照完整性的级别(可能不允许关闭非零余额的帐户,可能不允许余额为负等)的完整性根据需要增加复杂程度。我不是在谈论你的所有业务逻辑,只是禁止你觉得数据库永远不会因为客户端编程错误或者没有按正确的顺序做事或者用正确的参数调用东西而陷入的低级情况。

在真正的银行业务(即COBOL应用程序)中,通常是数据库模式(通常是非关系型和非规范化的 - 很多这些事情早于SQL),你会看到很多东西,例如12个月的过去余额桶,这些都是更新的帐户滚动时转移。这些系统使用的一些数据库是分层的。这是代码非常重要的地方,因为一切都在代码中完成。再一次,它有点过时,容易受到各种各样的问题的影响(可能很像NatWest正在经历的那样)而NoSQL是回归这种以代码为主的方式看待事物的趋势。经过很长一段时间处理这些事情后我才会想到 - 我不喜欢有缓存余额的系统,我不喜欢那些你真的没有时间点问责制的系统 - 即你忽略后的交易某个日期,你可以看到某个日期/时间的确切内容。

我确信有人拥有类似银行的数据库设计的“标准”模式,但我不知道他们多年来已经构建了几个类似会计的系统 - 账户和交易并不复杂而且一次超越这个概念,一切都得到高度定制。

例如,在某些情况下,根据GAAP和随时间支付的合同,您可能会根据某种时间表确认合同收益。在银行业,你有很多与利息相关的东西,不同的资金成本利率等。一旦你开始将业务需求与仅仅是金钱来龙去除的基本知识混合起来,一切都变得独特。

答案 1 :(得分:1)

您没有说明您的应用中是否在UI和数据库之间有中间层。如果这样做,您可以选择在何处标记交易并重新计算余额。如果此数据库由一个应用程序全资拥有,则可以将计算移动到中间层,只使用数据库进行持久化。

Spring是一个框架,它有一个很好的基于注释的方式来声明事务。它基于POJO; EJB的替代品。它是依赖注入,面向方面编程和优秀库的三脚凳。也许它可以帮助您构建和实现您的应用程序。

如果你有一个中间层,并且它是用面向对象的语言编写的,我建议你看一下Martin Fowler的“分析模式”。它已存在很长一段时间了,但今天关于金融系统的章节与首次编写时一样好。