Spring StateMachine学习(五) —— 持久化

本文介绍了如何在企业应用中使用Spring StateMachine处理复杂的流程,特别是使用choice进行条件判断。通过一个表单状态流程示例,展示了choice在状态转换中的作用,包括创建、填写、检查、提交等步骤。同时,探讨了在choice中使用Guard进行条件判断以及在状态变化时如何通过Action解耦业务处理。最后,展示了不同流程的结果。
摘要由CSDN通过智能技术生成

实际的企业应用中状态机的流程会更加复杂,而我们最常用到的就是choice。它类似于java的if语句,作为条件判断的分支而存在,让我们先看一张图:
在这里插入图片描述
这张图表现的是一个表单(form)的整个状态流程:

  • 创建初始的空白表单( BLANK_FORM)
  • 填写(WRITE)表单,成为填充完表单(FULL_FORM)
  • 检查(CHEKC)表单
    • 如果是表单名(formName)不为null,表单成为待提交表单(CONFIRM_FROM)
    • 提交(SUBMIT)表单,成为成功提交表单(SUCCESS_FORM)
  • 检查(CHECK)表单
    • 如果表单名为null,表单成为待处理表单(DEAL_FORM),修改formName
    • 处理(DEAL)表单
      • 如果表单名还是null或者里面有个“坏”字,表单状态变成废单(FAILED_FORM)
      • 如果表单名称没问题,表单状态变成填充完表单状态(FULL_FORM),重新走流程

大家不要在意这个例子的幼稚,毕竟它还是能用简单的方式体现出流程的复杂性(这话多么的辩证统一)。它有判断分支(还有两个),还有流程的循环,还有分支判断后的直接失败和分支判断后的后续环节,后面我们会在代码中告诉大家这里面需要注意的东西。

代码实现

先上状态机的四件套:States,Events,Builder和EventConfig(spring statemachine还是蛮简单的,来来回回就这几样东西)

public enum ComplexFormStates {
   
	BLANK_FORM, // 空白表单
	FULL_FORM, // 填写完表单
	CHECK_CHOICE,//表单校验判断
	DEAL_CHOICE,//表单处理校验
	DEAL_FORM,//待处理表单
	CONFIRM_FORM, // 校验完表单
	SUCCESS_FORM,// 成功表单
	FAILED_FORM//失败表单
}

注意一点,choice判断分支本身也是一种状态,要声明出来,这里是CHECK_CHOICE和DEAL_CHOICE

public enum ComplexFormEvents {
   
	WRITE, // 填写
	CHECK,//校验
	DEAL,//处理
	SUBMIT // 提交
}

同样的分支事件也要声明,这里是CHECK和DEAL。

大头是MachineBuilder,这个代码就比较多,大家最好对照着上面这张图来看,会比较清晰

/**
 * 复杂订单状态机构建器
 */
@Component
public class ComplexFormStateMachineBuilder {
   

	private final static String MACHINEID = "complexFormMachine";
	
	 /**
	  * 构建状态机
	  * 
	 * @param beanFactory
	 * @return
	 * @throws Exception
	 */
	public StateMachine<ComplexFormStates, ComplexFormEvents> build(BeanFactory beanFactory) throws Exception {
   
		 StateMachineBuilder.Builder<ComplexFormStates, ComplexFormEvents> builder = StateMachineBuilder.builder();
		 
		 System.out.println("构建复杂表单状态机");
		 
		 builder.configureConfiguration()
		 		.withConfiguration()
		 		.machineId(MACHINEID)
		 		.beanFactory(beanFactory);
		 
		 builder.configureStates()
		 			.withStates()
		 			.initial(ComplexFormStates.BLANK_FORM)
		 			.choice(ComplexFormStates.CHECK_CHOICE)
		 			.choice(ComplexFormStates.DEAL_CHOICE)
		 			.states(EnumSet.allOf(ComplexFormStates.class));
		 			
		 builder.configureTransitions()
					.withExternal()
						.source(ComplexFormStates.BLANK_FORM).target(ComplexFormStates.FULL_FORM)
						.event(ComplexFormEvents.WRITE)
						.and()
					.withExternal()
						.source(ComplexFormStates.FULL_FORM).target(ComplexFormStates.CHECK_CHOICE)
						.event(ComplexFormEvents.CHECK)
						.and()
					.withChoice()
						.source(ComplexFormStates.CHECK_CHOICE)
						.first(ComplexFormStates.CONFIRM_FORM, new ComplexFormCheckChoiceGuard())
						.last(ComplexFormStates.DEAL_FORM)
						.and()
					.withExternal()
						.source(ComplexFormStates.CONFIRM_FORM).target(ComplexFormStates.SUCCESS_FORM)
						.event(ComplexFormEvents.SUBMIT)
						.and()
					.withExternal()
						.source(ComplexFormStates.DEAL_FORM).target(ComplexFormStates.DEAL_CHOICE)
						.event(ComplexFormEvents.DEAL)
						.and()
					.withChoice()
						.source(ComplexFormStates.DEAL_CHOICE)
						.first(ComplexFormStates.FULL_FORM, new ComplexFormDealChoiceGuard())
						.last(ComplexFormStates.FAILED_FORM);
		 return builder.build();
	 }
}
  • 在我们熟悉的withExternal之后,我们迎来了为choice专门准备的withChoice()和跟随它的first(),last()。这两个代表的就是分支判断时TRUE和FALSE的状态流程去处,这里面涉及到的一个问题就是,TRUE和FALSE的判断条件是什么呢,根据啥来判断呢?
  • Guard就承担了这个判断的功能,看名字似乎不像。它在spring statemachine本来是用来保护这个状态跳转过程的,所以用guard,但在choice里面,它就是作为判断代码而存在的,代码如下:
public class ComplexFormCheckChoiceGuard implements Guard<ComplexFormStates, ComplexFormEvents> {
   

	@Override
	public boolean evaluate(StateContext<ComplexFormStates, ComplexFormEvents> context) {
   
		boolean returnValue = false;
		Form form = context.getMessage().getHead
  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值