架构设计-订单系统之业务的设计与实现

一、背景简介

订单业务一直都是系统研发中的核心模块,订单的产生过程,与系统中的很多模块都会高度关联,比如账户体系、支付中心、运营管理等,即便单看订单本身,也足够的复杂;

业务在发展的过程中,必然会导致订单量的持续增加,订单自身、数据体量、实现流程,都需要不断的迭代更新,如果在订单流程的研发初期,没有相对全面的考量,那么很有可能导致中后期的重构;

从实践经验上说,围绕订单业务:建议过度设计,轻量级分步实现

在产品初期先做好全面的设计,场景和流程上做好可扩展性的保留,在数据层面规划好不同体量的应对方案,走在订单业务的前面避免被动,尽量不要被业务的发展和演变甩在身后;

二、订单业务

1、订单体系

订单体系从角色上看,主要涉及:用户、商户、平台三个核心参与方,其订单流程的搭建就是围绕三方的交易场景展开;

这里需要说明一些细节:商户可以是第三方商家,也可以是平台方自己,不影响概念上的划分;商品也存在多种形式,所以用交付来描述,可以覆盖物流的定义;

用户:通过应用端,进行商品的选择和下单;平台:实现订单交易链路和支付能力,以及对整个流程的调度;商户:提供商品和交付能力;

在图中,只是围绕订单体系做一个框架性的宽泛描述,在成熟的订单业务中,其复杂程度远超上图,下面围绕核心节点来细致分析;

2、流程管理

2.1 流程拆分

订单的业务属性是极高的,流程本身也比较复杂,从不同的参与方来看,其流程分段策略完全不一样,这里仅站位研发视角,把订单逻辑分为:创建、支付、交付三个阶段;

  • 订单创建:围绕用户的下单路径做管理,从商品的访问点击并选中,到购车下单或者直接下单,从而完成订单的创建;
  • 订单支付:各种支付渠道的对接是交易场景的基础功能,订单的核心状态即支付成功;
  • 订单交付:在订单支付完成之后,开始进行商品的交付流程,可能是商家的发货或者服务提供,交付成功即订单完成;

如果将整个订单场景统筹起来看的话,还存在很多隐性的流程,与订单衔接的上下游业务还有很多,这里只是专注于订单功能自身的边界做划分;

2.2 正向流程

在理想的状态下,订单从购物车结算下单开始,到交易支付完成,最终到商家完成交付,是非常复杂的流程链路;

在实现上,订单的正向流程链路都是分段管理的,比如购物车、订单创建之后、支付完成、交付等诸多关键节点,并不是一个即时的流程;

2.3 逆向流程

对于订单这种极度复杂的流程,导致订单流程逆向的情况,要细致的考虑并且提供相应的解决方案,尽量确保程序可以兜底流程逆向,人工干预的成本和风险都极高;

  • 取消动作:用户主动取消订单,发起退款流程等;商户因为交付失败,主动发起流程退回等动作;
  • 超时情况:订单创建后,指定时间内没有支付;订单支付后,指定时间内商家没有交付等多个超时场景;
  • 节点异常:系统平台的在订单调度时的业务异常,或者程序异常,又或者支付等第三方渠道异常等;

这些常见的异常问题,在一般的场景下可能不会引发效应问题,对于订单这种异步解耦的复杂场景中,需要一个稳定的机制快速执行逆向流程;比如下单后未支付导致持续锁定库存,或者交付超时影响用户体验等;

2.4 调度与监控

订单属于核心流程又兼具复杂的特性,自然依赖系统平台的调度与监控手段,无论是正向还是逆向流程,都依赖调度手段提高订单的完成率,或者促使逆向流程有序执行,在这个过程中需要对订单路径有完整的监控能力;

调度机制:更侧重订单被动状态的处理,多见于各种超时的场景,用来提前对用户和商户进行消息提醒触达,或者进行订单流程的处理;

监控策略:更侧重对订单的主动干预处理,在发现订单中断或者异常时,可以通过产品层面的入口进行主动修复,或者系统层面的主动重试,当然也不排除最后的手动干预;

3、结构设计

围绕订单场景,涉及的数据结构非常复杂,不论是商品还是支付,亦或是订单自身的结构,在具体的业务中都会拓展出很多关联表;

订单结构的设计和管理,基于场景复杂度考虑,可能要融合商家、仓储货架、用户、渠道和类型等;在订单量增长之后,还需要结合业务场景,进行数据体量层面的拆分处理;

三、技术方案

1、订单ID

订单主体的唯一ID标识,在数据体量不大的情况下,使用表的自增ID主键即可,从长期看的话并不友好,如果订单量比较大,可能涉及分库分表的流程,则需要制定ID生成策略;

  • UUID:生成唯一字符串识别码,订单ID直接使用即可;
  • 雪花算法:分布式ID生成算法策略,生成的ID遵循时间的顺序;
  • 自定义ID:除了唯一的属性外,在订单ID中添加其他的关键业务标识;

2、并行与异步

并行操作,在订单详情的加载过程中,涉及到的查询信息非常多,比如:商品、商户、订单、用户等,可以通过并行的方式,提高响应的时间,如果采用串行的方式,则接口性能会差很多;

异步操作,订单是个复杂的流程,显然不可能在一次流程中完成所有逻辑,流程分段异步常规手段,就是借助MQ消息的方式,同样可以极大的提升服务性能;不论是订单的正逆向流程,都可以基于状态、事件、动作进行异步解耦处理;

3、超时问题

订单超时问题的本质在于,指定时间段之后需要执行一个动作;比如最经典的场景,下单之后超过15||30分钟未支付,订单自动取消并且被关闭,释放商品的库存,并通知用户;

实现一个动作延迟执行的方式有很多,比如延期队列,过期监听,消息延时消费等,不过这些方式在复杂的订单系统中并不常见,主流的话还是采用定时任务调度的方式;

任务调度时,对订单的处理,同样要确保业务流程操作的幂等性,数据层面的一致性等问题,如果出现异常单则进行重试,分析异常原因不断优化流程也同样重要;

如果订单体量大,任务调度能完成吗?

订单体量和订单实时量不是一个概念,系统沉淀的订单量和任务要处理的量不是一个等级,常规的数据体量做好分库分表的设计和查询优化即可,不会成为调度任务的瓶颈问题;

如果订单数据实时体量大,比如每天超千万的水平?

这就更不是应用的问题了,订单体量能达到每日千万的规模,公司会提前很长时间就把数据团队拉到应用团队中,解决这种核心的棘手问题,此前在数据公司搬砖时,每日单量刚过百万,就安排数据团队做解决方案了;

4、分布式事务

订单涉及支付对接、库存管理、结算对账等各种复杂的流程,自然对数据一致性有极高的要求,如果数据层面出现问题导致异常单出现,难免需要人工介入处理,所以对流程的各阶段做好细致的事务和逻辑管理极其重要;

订单流程是异步解耦的方式推进的,在分布式事务的策略上追求的是最终结果一致性即可,不过这并不妨碍在分段的流程中,进行局部的事务管理,事务成功,流程正向推进,事务失败,流程重试或逆向回滚;

四、数据方案

1、转化分析

经典的订单指标体系,用户下单过程的路径统计,从而深度的分析转化率问题,不断的对流程和场景优化,从而提高成交量;

交易的转化路径分析,是产品和运营重点关注的指标体系,在数据层面,埋点采集的数据通常是上传第三方平台,方便进行用户和业务分析,并且有助于同类客群的营销推广;

2、分库分表

数据在到达一定体量之后,需要进行分库分表的操作,从而解决各种性能方面的问题;将订单数据按照特定的维度进行计算,从而将数据分流到不同的库表中,解决读和写的瓶颈;

基于订单ID计算拆分的逻辑是最常见的,在特殊情况下,也会基于用户ID或商户ID进行计算,从而将相关的数据堆放在一起,如果有必要,也可以考虑多维度拆分的多写模式;

3、数据同步

订单数据分库分表虽然解决存储问题,但是也带来了很多查询方面的阻碍,通过搜索引擎来解决查询问题也是常用的技术选型;

订单数据在库和搜索引擎之间同步的方法有很多:同步双写,对数据的实时性要求极高;异步解耦,流程存在轻微的延迟;定时任务,存在明显的时效问题;组件同步,采用第三方数据同步组件;订单场景的话推荐同步双写的方式。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/809471.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Go gorm库(详细版)

目录 01. 什么是ORM 02. 环境搭建 03. 连接数据库 高级设置 gorm 的命名策略 创建表 日志显示 04. 模型定义 定义一张表 自动生成表结构 修改表字段大小 字段标签 05. 单表查询 5.1 表结构 5.2 添加单条记录 5.3 批量插入 5.4 单条数据查询 5.5 根据主键查询…

Vue3学习03 pinia

Vue3学习 pinia pinia一个简单效果搭建 pinia 环境存储读取数据示例 修改数据 (三种方式)storeToRefsgetters$subscribestore组合式写法 pinia 在vue2中使用vuex,在vue3中使用pinia。 集中式状态管理,(状态数据)。多个组件共享数…

多态【C/C++复习版】

目录 一、多态是什么?如何实现? 二、 什么是重写?有什么特点? 三、什么是协变? 四、析构函数能实现多态吗?为什么要实现? 五、override和final的作用是什么? 六、 多态的原理是…

Linux下网络编程基础知识--协议

网络基础 这一个课程的笔记 相关文章 协议 Socket编程 高并发服务器实现 线程池 协议 一组规则, 数据传输和数据的解释的规则。 比如说依次发送文件的文件名, 文件的大小, 以及实际的文件, 这样规定发送一个文件的顺序以及发送的每一个部分的格式等可以算是一种协议 型协议 …

防火墙用户管理技术——AAA

目录 一.AAA功能 (1).认证方式 (2).授权方式 (3).计费方式 二.RADUIUS协议 三.用户组织架构及管理 管理员认证登录方式 1.console 2.web 3.telnet 4.ssh 5.ftp 四.认证方式 五.AAA远程登录 1.端口添加IP地址达到互通 2.AAA视图进行配置 3.结果​编辑 一.AAA功能…

Android源码解析之截屏事件流程

今天这篇文章我们主要讲一下Android系统中的截屏事件处理流程。用过android系统手机的同学应该都知道,一般的android手机按下音量减少键和电源按键就会触发截屏事件(国内定制机做个修改的这里就不做考虑了)。那么这里的截屏事件是如何触发的呢…

【Redis深度解析】揭秘Cluster(集群):原理、机制与实战优化

Redis Cluster是Redis官方提供的分布式解决方案,通过数据分片与节点间通信机制,实现了水平扩展、高可用与数据容灾。本文将深入剖析Redis Cluster的工作原理、核心机制,并结合实战经验分享优化策略,为您打造坚实可靠的Redis分布式…

双数据库的安装

双MySQL的安装 【0】前言 ​ 本地已经安装过mysql5.1版本,应项目需求需要安装mysql5.7版本; ​ 官方网站下载对应版本:https://downloads.mysql.com/archives/community/ 【1】压缩包下载完成后解压至本地磁盘 【2】进入根目录下bin文件夹…

Flask基于flask_login实现登录、验证码

flask_login 是一个 Flask 扩展,用于在 Flask web 应用中实现用户会话管理。它允许你跟踪哪些用户已经登录,并管理他们的登录状态。flask_login 提供了用户认证的基础结构,但具体的用户验证(如用户名和密码检查)和存储…

泽众Testone自动化测试平台,测试用例支持单个调试执行,同步查看执行日志

泽众Testone自动化测试平台之前版本,测试用例批量和单个执行,必须要通过测试集操作执行,操作略繁琐,我们通过本轮优化升级,测试用例直接可以单个调试执行,同步查看执行日志,操作上去繁就简&…

OJ刷题日记:1、双指针(1)

目录 1、283.移动零 2、1089.复写零 3、202.快乐数 1、283.移动零 题目: 给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序。 请注意 ,必须在不复制数组的情况下原地对数组进行操作。 …

第十届 蓝桥杯 单片机设计与开发项目 省赛

第十届 蓝桥杯 单片机设计与开发项目 省赛 输入: 频率信号输入模拟电压输入 输出(包含各种显示功能): LED显示SEG显示DAC输出 01 数码管显示问题:数据类型 bit Seg_Disp_Mode;//0-频率显示界面 1-电压显示界面 un…

电脑无法开机?原因分析与解决方案

电脑无法开机是一种常见的问题,可能会给用户带来诸多困扰。无法启动可能是由于硬件故障、软件问题或者其他未知原因引起的。在本文中,我们将介绍三种常见的方法来解决电脑无法开机的问题,以帮助用户尽快恢复正常使用。 方法1:检查…

什么是队列

队列是一种特殊类型的线性表,其只允许在一端进行插入操作,而在另一端进行删除操作。具体来说,允许插入的一端称为队尾,而允许删除的一端称为队头。这种数据结构遵循“先进先出”(FIFO)的原则,即…

ubuntu安装irtualbox注意事项

下载官网7.0版本,ubuntu22.04,安装一直出错误,查到了下面兄弟的办法,仍然不幸,最后使用apt重装,请按第二部分流程安装,安装6.1,可以用 第一部分,反正我是没搞通,7.0反复的出现相同的…

C语言读取 .ico 文件并显示数据

原来是想做光标编辑器&#xff0c;自己把绘图板的内容导出为光标格式 鼠标指针文件格式解析——Windows&#xff08;一&#xff09; (qq.com) 代码来源自 Icons | Microsoft Learn 鄙人又补充些变量可以运行微软的代码 简单代码如下 #include <stdio.h> #include &l…

神经网络模型底层原理与实现8-BERT

首先介绍什么是自监督学习&#xff1a; 普通的有监督学习是每个x对应有个y&#xff0c;x训练得到y&#xff0c;将y与y作比较&#xff0c;而自监督是没有对应y&#xff0c;直接把一部分样本x作为训练目标x&#xff0c;训练得x后和x对比 bert中如何创造x&#xff1a;以文字处理为…

4/11 QT_day5

服务器端 头文件 #ifndef WIDGET_H #define WIDGET_H#include <QWidget> #include <QTcpServer> #include <QMessageBox> #include <QTcpSocket> #include <QList> QT_BEGIN_NAMESPACE namespace Ui { class Widget; } QT_END_NAMESPACEclass …

MSTP/RSTP与STP的兼容性

原理概述 MSTP(Multiple STP)协议和RSTP(Rapid STP)协议都可以向下兼容STP&#xff08;Spanning Tree Protocol &#xff09;协议。运行MSTP/RSTP协议的交换机会根据收到的BPDU版本号信息自动判断与之相连的交换机的运行模式。如果收到的是STP BPDU&#xff0c;MSTP/RSTP交换机…

Oracle 21c 数据库迁移到DM8(达梦)数据库

一、环境准备 1、创建脚本 执行dmCreateUser.sql脚本创建GLJ用户&#xff08;注意&#xff1a;需要与需要迁移的oracle用户名一样&#xff09;&#xff0c;如&#xff0c;脚本内容如下&#xff1a; -- 开始将输出重定向到指定的日志文件 spool start /home/dmdba/dmdbms/sql/…