DDD valueObject和数据库模式

时间:2014-12-31 14:12:22

标签: java database domain-driven-design

为了结束2014年,我想到了一个简单的问题。 我想更多地使用“DDD”,我正在尝试使用各种用例来了解有关DDD的更多信息。

我目前的用例如下:

  • 我们有一个新的数据库模式,它使用我们公司的经典模式:将我们的命名表建模为“id / code / label”。我认为这在使用hibernate时非常经典。

但是在OO世界中,当使用像JDBC或QueryDSL这样的API时,事情变得“复杂化”。我需要通过代码获取对象,检索其id或加载完整对象,然后将其设置为另一个对象中的一对一关系。

我想知道:

  • 这种命名法可以是枚举(或具有字符串cosnatnts的类,具体取决于开发人员)。在DDD术语中,它是我的ValueObject
  • 数据库中的id / code / label不是友好的(这不是先决条件)所以我没有看到它的优点。除非表可以动态更新,并且用例是“从这个表中加载的组合框中选择一些东西并与另一个对象建立关系:但这就是全部,因为如果你有必须应用的业务规则,你需要知道新的代码等等。)。

我的问题是:

  • 您经常在数据库模型中使用id / ocde / label模式吗?
  • 您如何为您的术语数据建模? (国家可能不是最好的例子:)但无论你怎么建模它?没有多想我会说国家的数据库表;但对于某些状态:“有效,等待验证,拒绝”?
  • 您是否使用此模式对valueObjects建模?
  • 或者您是否使用了大量的枚举并且只将它们的toString(或序数)存储在数据库中?

在Java OO对象世界中,我目前认为操作枚举从数据库加载的对象更容易。我需要构建存储库来加载它们。将它们用作枚举将非常简单。我在这里寻找一些建议,或者我错过了一些如此明显的东西?

感谢

在2015年见到你!

更新1: 我们可以创建一个“预算”,第一个标记为Initial,下一个标记为“Corrective”(带增量)。例如,我们可以列出预算:“初始预算”,“纠正预算#1”,“纠正预算#2”。

为此我们有这个数据库设计:一个预算表,一个版本Budge,两者之间有一个外键。版本预算仅包含ID,CODE和LABEL。

Personnaly,我想删除此表。我没有看到这种结构的优点。从OO的角度来看,当我创建预算时,我可以查询数据库以查看是否需要创建初始或纠正预算(使用计数查询),然后我可以将正确的枚举设置为我的新预算。但是对于当前的设计,我需要使用我想要的CODE查询数据库,选择ID并设置ID。所以是的,它确实是面向数据库的。 DDD部分在哪里? ValueObject是描述,量化某些东西的东西。在我看来,对我来说似乎很好。版本描述了我的预算的当前状态。我可以只修改两个版本,但检查他们的代码,他们没有生命周期(我特别不想要这个版本)。

如何处理此类用例?

这只是一个简单的例子,因为我发现,如果你问一个数据库管理员,他肯定会说一切似乎都很好:使用主键,建模关系,强制约束,使用外键并避免数据重复。

再次感谢Mike和Doctor的评论。

1 个答案:

答案 0 :(得分:0)

我将在你的国家示例中加入。在大多数情况下,国家将是一个价值对象。没有任何内容可以引用国家实体,而且应该知道,如果国家的价值发生变化,它仍然是同一个国家。实际上,该国家可以表示为枚举,以及一​​些令人讨厌的资源查找功能,它们将Iso3转换为有用的显示文本。我们所做的是,我们将它定义为具有iso3,displayname和一些其他静态信息的值对象类。现在,在这个价值对象之外,我们定义了一种" power enum" (我仍然怀念这里的标准术语)。实现country value对象的类获取私有构造函数和每个值(对于每个国家/地区)的静态属性以及从int到int的显式强制转换运算符。现在,您可以像处理编程语言的常规枚举一样对待它。除了具有更多属性字段之外,普通枚举的优点是,它还可以具有方法(当然是查询方法,不改变对象的状态)。您甚至可以使用多态(一些行为与其他行为不同的国家/地区)。您还可以从数据库表中加载枚举的内容(不使用静态,而是使用静态lookupByIso3方法)。

这可以和其他一些"枚举类似"价值对象。想象一下货币(它可能具有多态的转换方法)。然而,每日汇率的处理是一个不同的主题。

如果这组值不固定(例如另一个值对象候选者,如邮政地址),则它不是值对象枚举,而是可以使用您想要的值实例化的标准值对象。

要确定您是否可以将某些内容作为值对象,您可以使用以下问题:您想要复制语义还是引用语义?如果您更改了对象的属性,那么您使用它的所有位置是否也应该更新,或者它们应该保持原样?如果是后者,那么"改变了#34; object是一个新的不同的值对象。另一个问题是,如果你需要跟踪一个对象的变化,意识到它仍然是相同的"尽管价值观有所改变。如果你有一个值对象,你只想要存在特定的实例,那么它就是上面描述的一种枚举。

这对你有什么帮助吗?