聚会数据
Repository 在 DDD 中是一个非常特殊的存在,它能加载一个完整的聚合根和持久化修改后的聚合根。
这就必须要窥探聚合根的内部状态,但DDD中又表示聚合根的数据外部无法访问,这就相互矛盾,反直觉。如何解决呢?
约定get和set方法
我们可以约定,在 Repository 代码中,聚合根提供 set 方法和 get 方法支持加载和持久化所需要的聚合属性,同时聚合根提供一个无参构造器。get、set方法不可有任何业务逻辑,且仅仅只给 Repository 使用。
风险
这是一种妥协但简单方式。但这会让基础层里暴露了聚合根对象,完全依赖开发人员的责任感,否则聚合根的属性变得不可控。
那有没有其他方法呢?软件行业流行一句话:如果解决不了,就加一层。
聚合数据中转
引入聚合数据 AggregateData ,把聚合数据传给 Repository。
聚合根注解使用 dataType:被标记的聚合根将会转换为此值类型。 同时添加转换器,指定需要转换的属性(一般来说都是一一对应的)。
如:
@AggregateRoot(dataType = UserData.class)
需要一个转换器,将聚会根和聚合数据进行转换
同时在基础层中,暴露的就是聚会数据对象,而不是聚会根了。这样就防止聚会根外流。
自动生成
引入以下包,然后再maven
- Maven
<dependency>
<groupId>net.qiqb.framework</groupId>
<artifactId>qiqb-gen</artifactId>
<version>${lastVersion}</version>
<scope>provided</scope>
</dependency>
通过maven 编译,自动生成聚合数据类,无需创建。
聚合数据的自动生成规则:
@AggregateRoot注解 autoGenerateData 必须开启。- 聚会根类型必须有一个
protected无参构造器。 - 生成的聚合数据类在聚合根同包名下,名称默认:聚会根类名+Data。同时会创建聚会根引用的其他 entity 类型。
- 只会复制
protected的字段。 - 聚会根内的属性,值对象直接引用(浅copy),实体类属性会重新创建(深copy)。