Java 处理Axon中的非平凡命令和事件有效负载
每当我看一眼,我就会开始思考是否应该遵循一组事件和命令的设计规则 在Axon Bank中,事件和命令完全由原语组成。在我的应用程序中,我倾向于尽可能避免原始用法,主要是为了构建一个表达域,并在任何我能得到的地方都具有类型安全性 Axon本身附带了一些DDD引用,但无论我浏览哪个文档,都没有一个示例将复合对象用作事件/命令有效负载的一部分 这让我很困惑。它内置了对全面的xml和json序列化的支持,不仅能够拥有一些键值对 我理解,尤其是事件往往是小而简单的结构,因为它们只反映增量状态更改,但在复杂域模型和事件(条目)之间总会有某种差距Java 处理Axon中的非平凡命令和事件有效负载,java,spring,axon,Java,Spring,Axon,每当我看一眼,我就会开始思考是否应该遵循一组事件和命令的设计规则 在Axon Bank中,事件和命令完全由原语组成。在我的应用程序中,我倾向于尽可能避免原始用法,主要是为了构建一个表达域,并在任何我能得到的地方都具有类型安全性 Axon本身附带了一些DDD引用,但无论我浏览哪个文档,都没有一个示例将复合对象用作事件/命令有效负载的一部分 这让我很困惑。它内置了对全面的xml和json序列化的支持,不仅能够拥有一些键值对 我理解,尤其是事件往往是小而简单的结构,因为它们只反映增量状态更改,但在复杂
在我的领域中,我可以有很多类,比如
透支限额
,当前余额
,存款
和账户标识符
现在有两种可能的方法来设计事件和命令:
1.基元与广义转换
- 将事件视为原始数据,并在其上添加一个漂亮的标签
- 一旦原始数据“进入”应用程序,就将其转换为功能强大的对象
- 创建事件时,只需再次将其剥离
在其他地方:public class BankAccountcreatedEvent { private final String accountIdentifier; private final int overdraftLimt; // ... }
public void on (BankAccountCreatedEvent event) { this.accountIdentifier = AccountIentifier.fromString(event.getAccountIdentifier()); this.overdraftLimit = new OverdraftLimit(event.getOverdraftLimit()); }
- 没有任何奇怪依赖项的简单命令/事件API
- 使分发更容易
- 只有当实际事件结构发生变化,因此可以很容易地预测时,才需要向上广播
- 需要编写和维护一个巨大的转换层
- 由于主要技术原因,将事件/命令与域模型的其余部分分离会引入一个新的、人为的上下文间隙
- 直接使用复杂类型作为属性
public class BankAccountCreatedEvent { private final BankAccountIdentifier bankAccountIdentifier; private final OverdraftLimit overdraftLimit; //.. }
- 写得少,读起来容易
- 把本来应该在一起的东西放在一起
- 域逻辑间接地影响事件结构,需要更频繁地进行向上转换,并且不太可预测
我需要第二个意见。有推荐的方式吗?首先要记住的是,活动的序列化形式是您的正式合同。在Java类中如何表示这一点最终取决于每个应用程序。例如,如果将序列化程序配置为忽略未知字段,则可以将不关心的字段保留在外
public class BankAccountCreatedEvent {
private final BankAccountIdentifier bankAccountIdentifier;
private final OverdraftLimit overdraftLimit;
//..
}
就我个人而言,我不介意事件中的原语。但是,我确实理解在某些字段中使用显式值对象的价值,因为它们允许您表达每个字段所涉及的“数学”。在标识符的情况下,它们可以防止“混淆”,即标识符被用于意外地尝试标识另一种类型的对象
最后,这没什么大不了的。通过一些简单的Jackson注释,您可以将这些值对象转换为JSON中的简单值。例如,退房
public class BankAccountCreatedEvent {
private final BankAccountIdentifier bankAccountIdentifier;
private final OverdraftLimit overdraftLimit;
//..
}
将映射到:
{
"bankAccountIdentifier": "abcdef1234",
"overdraftLimit" : 1000
}
如果BankAccountIdentifier和OverdraftLimit类都有@JsonValue注释方法,该方法将返回它们的“简单”值