中石化工建设宁波分公司网站物流系统规划课程建设网站

张小明 2026/1/12 15:14:22
中石化工建设宁波分公司网站,物流系统规划课程建设网站,灵寿网站建设,网站建设有多少公司背景本文将基于借款订单状态流转这个场景来实现。如果使用if-else或者switch语句来处理这些状态#xff0c;代码会变得非常臃肿且难以维护。而状态机提供了一种更加结构化和可维护的方式来管理这些状态转换。示例中涉及到#xff1a;状态机的配置、数据持久化、状态恢复查询、…背景本文将基于借款订单状态流转这个场景来实现。如果使用if-else或者switch语句来处理这些状态代码会变得非常臃肿且难以维护。而状态机提供了一种更加结构化和可维护的方式来管理这些状态转换。示例中涉及到状态机的配置、数据持久化、状态恢复查询、同一事件由同一sourceStatus流转到不同targetStatusSpringBoot集成状态机1、首先需要添加Spring Statemachine的依赖到Spring Boot项目的pom.xml文件中dependency groupIdorg.springframework.statemachine/groupId artifactIdspring-statemachine-core/artifactId version4.0.0/version /dependency2、定义系统中订单存在的状态public enum OrderStatusEnum { // 待审核 APPROVE_PENDING, // 审核中 APPROVE_ING, // 审核失败 APPROVE_FAILED, // 审核成功 APPROVE_SUCCESS; }3、定义系统中触发状态变更的事件public enum OrderEvent { // 开始审核 APPROVE_START, // 审核通过 APPROVE_SUCCESS, // 审核失败 APPROVE_FAILED; }4、状态机-状态流转配置Configuration EnableStateMachine(name OrderStateMachine) Slf4j publicclass OrderStateMachineConfig extends EnumStateMachineConfigurerAdapterOrderStatusEnum, OrderEvent { Resource private OrderMapper orderMapper; /** * 配置状态 * * param states * throws Exception */ Override public void configure(StateMachineStateConfigurerOrderStatusEnum, OrderEvent states) throws Exception { states.withStates() .initial(OrderStatusEnum.LOAN_PENDING) // 设置初始状态为[待审核] .states(EnumSet.allOf(OrderStatusEnum.class)); } /** * 配置状态转换事件关系 * * param transitions * throws Exception */ Override public void configure(StateMachineTransitionConfigurerOrderStatusEnum, OrderEvent transitions) throws Exception { transitions //当执行 【开始审核】操作时将订单状态由待审核 - 审核中 .withExternal().source(OrderStatusEnum.APPROVE_PENDING).target(OrderStatusEnum.APPROVE_ING).event(OrderEvent.APPROVE_START) .and() //当执行 【审核失败】操作时将订单状态由审核中 - 审核失败 .withExternal().source(OrderStatusEnum.APPROVE_ING).target(OrderStatusEnum.APPROVE_FAILED).event(OrderEvent.APPROVE_FAILED) .and() //当执行 【审核成功】操作时将订单状态由审核中 - 审核成功 .withExternal().source(OrderStatusEnum.APPROVE_ING).target(OrderStatusEnum.APPROVE_SUCCESS).event(OrderEvent.APPROVE_SUCCESS); } /** * 持久化配置 * * return */ Bean public DefaultStateMachinePersister persister() { returnnew DefaultStateMachinePersister(new StateMachinePersistOrderStatusEnum, OrderEvent, BizOrder() { Override public void write(StateMachineContextOrderStatusEnum, OrderEvent context, BizOrder order) throws Exception { OrderStatusEnum orderStatus context.getState(); log.info(订单状态持久化,订单ID{},目标状态:{}, order.getId(), orderStatus); orderMapper.updateOrderStatus(order.getId(), orderStatus); } Override public StateMachineContextOrderStatusEnum, OrderEvent read(BizOrder order) throws Exception { log.info(恢复订单状态机状态); returnnew DefaultStateMachineContext(order.getStatus(), null, null, null); } }); } }5、新建一个变更订单状态的服务public interface BizOrderStatusService { /** * * 通用状态变更处理器 * param incomingId * param event */ void eventHandler(Long orderId, OrderEvent event); }Service publicclass BizOrderStatusServiceImpl implements BizOrderStatusService { Resource private OrderMapper orderMapper; Resource private StateMachineOrderStatusEnum, OrderEvent orderStateMachine; Resource private StateMachinePersisterOrderStatusEnum, OrderEvent, BizOrder persister; /** * * * param orderId 订单id * param event 事件类型 */ Override public void eventHandler(Long orderId, OrderEvent event) { BizOrder order orderMapper.getOrderById(orderId); Assert.notNull(order, 订单不存在); // 自定义状态机参数对象(可以在此对象中定义后续需要用到的字段参数状态配置那里如果需要做业务逻辑判断) StateMachineParam param new StateMachineParam(); param.setBizOrder(order); Message message MessageBuilder.withPayload(event).build(); if (!sendEvent(message, param)) { thrownew ApplicationBizException(订单状态流转异常); } } /** * 发送订单状态转换事件 这里不要使用synchronized锁方法效率比较低 * 分布式系统优先采用分布式锁下单锁userId订单状态流转锁orderId根据业务考虑使用什么。 * * param message * param param * return */ private synchronized boolean sendEvent(MessageOrderEvent message, StateMachineParam param) { boolean result false; try { orderStateMachine.start(); //尝试恢复状态机状态 persister.restore(orderStateMachine, param.getBizOrder()); orderStateMachine.getExtendedState().getVariables().put(param, param); result orderStateMachine.sendEvent(message); //持久化状态机状态 persister.persist(orderStateMachine, param.getBizOrder()); } catch (Exception e) { e.printStackTrace(); } finally { orderStateMachine.stop(); } return result; } }6、调用方法执行订单状态变更并持久化到数据库RestController RequiredArgsConstructor publicclass ApproveController { privatefinal OrderStatusService orderStatusService; /** * 前端调用start方法将订单状态改为审核中并自动持久化到数据库 * param orderId 订单id * return */ PostMapping(/start) public void start(Long orderId) { orderStatusService.eventHandler(orderId,OrderEvent.APPROVE_START); } /** * 前端调用start方法将订单状态改为审核成功并自动持久化到数据库 * param orderId 订单id * return */ PostMapping(/approveSuccess) public void approveSuccess(Long orderId) { orderStatusService.eventHandler(orderId,OrderEvent.APPROVE_SUCCESS); } /** * 前端调用start方法将订单状态改为审核失败并自动持久化到数据库 * param orderId 订单id * return */ PostMapping(/approveFailed) public void approveFailed(Long orderId) { orderStatusService.eventHandler(orderId,OrderEvent.APPROVE_FAILED); } }现在我们已经配置了状态机并创建了服务来操作它。接下来你可以在应用的任何部分注入OrderStatusService并传入相应的事件来改变订单的状态。7、总结以上就是状态机的基础用法一个事件对应一种来源状态(sourceStatus)和目标状态(targetStatus)。在我自己使用到的场景中还包含一个事件需要根据不同的条件将同一来源状态流转到不同的目标状态。这时我们就需要在状态映射配置中增加业务逻辑判断。8、扩展新增一个放款事件该事件会将订单状态由【审核成功】流转到【放款成功】或者【部分放款成功】具体流流转哪一个状态是由订单的放款金额决定的如果申请金额和放款金额一致就是【放款成功】放款金额小于申请金额就是【部分放款成功】8.1 我们在订单状态枚举中新增(LOAN_SUCCESS,PARTIALLY_LOAN_SUCCESS)// 待审核 APPROVE_PENDING, // 审核中 APPROVE_ING, // 审核失败 APPROVE_FAILED, // 审核成功 APPROVE_SUCCESS, // 放款成功 LOAN_SUCCESS, // 部分放款成功 PARTIALLY_LOAN_SUCCESS;8.2 我们在事件枚举中新增(LOAN)// 开始审核 APPROVE_START, // 审核通过 APPROVE_SUCCESS, // 审核失败 APPROVE_FAILED, // 操作放款 LOAN;8.3 优化一下上面的【配置状态转换事件关系】需要在事件后面增加条件判断(通过guard()实现)/** * 配置状态转换事件关系 * * param transitions * throws Exception */ Override public void configure(StateMachineTransitionConfigurerOrderStatusEnum, OrderEvent transitions) throws Exception { transitions //当执行 【开始审核】操作时将订单状态由待审核 - 审核中 .withExternal().source(OrderStatusEnum.APPROVE_PENDING).target(OrderStatusEnum.APPROVE_ING).event(OrderEvent.APPROVE_START) .and() //当执行 【审核失败】操作时将订单状态由审核中 - 审核失败 .withExternal().source(OrderStatusEnum.APPROVE_ING).target(OrderStatusEnum.APPROVE_FAILED).event(OrderEvent.APPROVE_FAILED) .and() //当执行 【审核成功】操作时将订单状态由审核中 - 审核成功 .withExternal().source(OrderStatusEnum.APPROVE_ING).target(OrderStatusEnum.APPROVE_SUCCESS).event(OrderEvent.APPROVE_SUCCESS) .and() //当执行 【放款】操作时将订单状态由审核成功 - 放款成功 .withExternal().source(OrderStatusEnum.APPROVE_SUCCESS).target(OrderStatusEnum.LOAN_SUCCESS).event(OrderEvent.LOAN).guard(guardForLoanSuccessByLoan()) .and() //当执行 【放款】操作时将订单状态由审核成功 - 部分放款成功 .withExternal().source(OrderStatusEnum.APPROVE_SUCCESS).target(OrderStatusEnum.PARTIALLY_LOAN_SUCCESS).event(OrderEvent.LOAN).guard(guardForPartiallyLoanSuccessByLoan()); } /** * 订单状态由审核通过 - 放款成功 * 触发条件订单申请金额放款金额 * * return */ Bean public GuardOrderStatusEnum, OrderEvent guardForLoanSuccessByLoan() { return context - { // 从扩展信息中获取参数 StateMachineParam param (StateMachineParam) context.getExtendedState().getVariables().get(param); BizOrder order param.getBizOrder(); // 如果申请金额放款金额 返回true状态机就会流转到调用此方法的目标状态 if (order.getApplyAmount().compareTo(order.getLoanAmlunt) 0) { returntrue; } returnfalse; }; } /** * 订单状态由审核通过 - 部分放款成功 * 触发条件订单申请金额放款金额 * * return */ Bean public GuardOrderStatusEnum, OrderEvent guardForPartiallyLoanSuccessByLoan() { return context - { // 从扩展信息中获取参数 StateMachineParam param (StateMachineParam) context.getExtendedState().getVariables().get(param); BizOrder order param.getBizOrder(); // 如果申请金额放款金额 返回true状态机就会流转到调用此方法的目标状态 if (order.getApplyAmount().compareTo(order.getLoanAmlunt) 0) { returntrue; } returnfalse; }; }通过以上操作我们就可以实现业务中某些需要根据不同条件流转到不同状态的场景。
版权声明:本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!

网页编辑软件哪个好景德镇seo

Java数据可视化终极指南:5分钟快速上手XChart图表库 【免费下载链接】XChart 项目地址: https://gitcode.com/gh_mirrors/xch/XChart 还在为Java项目中枯燥的数据展示而烦恼吗?想要将复杂的数据转化为直观生动的图表吗?XChart作为一款…

张小明 2026/1/1 15:07:23 网站建设

济宁网站建设怎么样wordpress tag做专题

做独立站的人,基本都绕不开几个现实问题: 想要一个“看起来高级”的前端,但不想从零写购物车、结账流程 想要支付闭环(尤其是信用卡/国际支付),又不想被各种平台限制 想要页面加载快、SEO 友好、可二次开发 还希望部署简单,方便后续扩展营销、会员、优惠码、埋点分析…

张小明 2025/12/24 23:19:42 网站建设

郑州网站建设 天强科技资阳网站建设公司

免费服装设计软件Valentina:5分钟快速上手完整指南 【免费下载链接】fashionmaker Fashion Robot 项目地址: https://gitcode.com/gh_mirrors/fa/fashionmaker Valentina是一款功能强大的开源服装设计软件,专为服装设计师、制版师和时尚爱好者打造…

张小明 2026/1/8 2:56:51 网站建设

读书网站排名网站正在建设中的图片大全

在Android使用过程中,你是否曾因"无法截屏"的提示而束手无策?许多应用为了保护隐私或重要内容,设置了系统级的截屏限制功能。今天,我们将深入探讨一个专为解决这一痛点而生的开源工具——DisableFlagSecure,…

张小明 2026/1/10 16:15:37 网站建设

网站设计例子哪里有个人做网站的

ElectronBot桌面机器人轴承安装终极实战:从问题诊断到完美运行的完整探秘 【免费下载链接】ElectronBot 项目地址: https://gitcode.com/gh_mirrors/el/ElectronBot 想要让你的ElectronBot桌面机器人动作如丝般顺滑吗?在组装过程中,轴…

张小明 2025/12/25 1:15:51 网站建设

宁波cms模板建站用PS怎么做网站图片

第一章:从崩溃到稳定的转折点系统在经历连续72小时的异常宕机后,终于迎来了关键的修复契机。这次故障源于一次未经充分测试的配置推送,导致服务链路中核心网关节点过载崩溃。团队在紧急回滚后,开始深入分析日志与监控数据&#xf…

张小明 2025/12/30 20:57:36 网站建设