首页 > 解决方案 > 管理 JPA 实体的 Spring 状态机

问题描述

我有一个具有字段的TaskJPA - 所以看起来状态机可能是很好的抽象。可以通过以. 我想利用 的概念,因为它看起来像很好的抽象。我想我需要一些东西:@EntitystatestatePUT /api/tasks/{id}/stateActionsGuards

  1. 在 REST 端点中创建(或者更确切地说是恢复?)状态机对应于当前Tasks的状态并将 JPA 实体与其上下文相关联,因此它可用于Actions 可以更改state任务的状态字段(和其他)并持久化它通过Repository
  2. 发送表示转换到新状态的事件

我假设第 1 点将通过构建器创建机器,就像使用 @EnableStateMachineFactory 一样,您无法真正在特定状态下创建机器(哪种有意义)。我不清楚如何将我可能findOne在状态机上下文中的实体添加@Repository到状态机的上下文中。

那是正确的方法吗?有没有涵盖这个的样本?我很诚实地浏览了现有的样本,没有发现任何类似的东西。

标签: javaspring-statemachine

解决方案


你应该首先问自己——你真的真的需要一个状态机吗(我不知道你的完整用例)。这StateMachine将在您的代码中引入一些(很多?)复杂性。

话虽如此,这是一个可能的设计:

1) 为实体实现您的标准 SOA(例如TaskController-> TaskService-> TaskRepository)。

2)创建一个Service (W),其唯一目的是创建事件并将它们发送给SM。在那里Service (W),您将拥有SM factory注入的和TaskService(用于加载现有的状态Task)。

4) 当 Request/Event 被发送到 时TaskController,你会调用Service (W),它将执行以下操作:

  • 实例化一个新的 SM,如果Task存在,用任务的状态重新水化 SM的状态
  • 一旦 SM 被初始化,发送事件

5) 在状态机配置中,您将拥有与该事件关联的源、目标和操作。该操作将调用TaskService并更新 JPA 实体。

如果您在需要更新实体时有复杂的业务规则并且您希望可能的状态转换是确定性的(例如,您有一个预定义的工作流或状态图),那么这种设计是有意义的。每个状态转换之前的业务规则可以抽象为警卫,SM 可以是其他人与您的 JPA 实体交互(更新)的接口。

对于 JPA Entity 中的状态机再水化,请参阅此答案


推荐阅读