高并发架构实战(一) 电商系统设计

释放双眼,带上耳机,听听看~!

转载请标注原文地址:https://blog.csdn.net/lilyssh/article/details/82753318

电商平台微服务架构设计

按照孢子框架要义对电商平台进行微服务架构设计。假设我们设计的目标是简易版淘宝。

1. 需求分析

由于主要是学习技术,所以没对业务规划得过于详细和全面。大的功能分为三个,用户、商品、订单。主要需求如下:

前端首页
注册
及时响应、安全性
 
商品展示
及时响应、搜索引擎优化
 
商品搜索
及时响应、搜索引擎优化
 
秒杀购买商品
及时响应、安全性、可靠性
用户中心
我的订单
及时响应、安全性

2. 系统分析

要将需求进行系统分析,还需要有企业的运营目标做支持。假设我们运营目标是:

  • 用户量:3000万
  • 网站日访问量:3000万PV
  • 商品购买并发:1000 QPS

我们按照上面的需求进行系统分析,首先按大的职责将职责相同的划分为一个服务。并且有了上面这个运营目标,所有功能需求都需要增加一项“质量”特性,那就是“高并发”,高并发会影响到所有设计。安全性和可靠性也会直接影响功能的技术实现,但并没有并发性影响性大。深入分析职责后把每一种功能的实现关键技术列出,如下:

前端首页
商品展示、商品搜索
商品系统
集群部署、高速缓存、分布式缓存、搜索引擎技术、静态化
 
秒杀购买商品
订单系统
集群部署、消息队列、实时计算
用户中心
我的订单
订单系统
集群部署

如上所述,要支持运营目标的电商平台,可以分为大小几个服务和子系统。系统划分的依据一方面是职责,一方面跟实现技术有关,同一职责下实现技术不同会被划分为两个服务,比如购买商品和商品展示原本属于同一个大的领域,但其因为实现技术和质量要求不同需要划分为两个模块。这是因为微服务和传统SOA最大的区别就是技术实现的个性化,只有个性化才能做好做专,并节省成本。用户购买产品产生订单相关数据,订单数据关系到商品和用户两方面,如果是超高并发的系统,用户购买行为需要单独的服务。

3. 逻辑架构

逻辑视图采用以下方法建立。
高并发架构实战(一) 电商系统设计
按照职责、通用性、技能及工作量综合考虑和计量,平台逻辑架构设计如下图:
高并发架构实战(一) 电商系统设计
用户通过终端层发起请求,请求经由网关层nginx,路由到业务层,业务层通过业务逻辑判断,再访问数据访问层,数据访问层再通过数据库层获取到想要的内容。

  • 使用kafka,可优化下单性能,可以处理秒抢,或者异步处理一些事情,如送下单后优惠券。
  • 使用Elasticsearch,可优化商品查询,商品一般数据量比较大,用户经常模糊查询,近义词要能查出来,且要求及时响应,Elasticsearch正好能解决这种难题,所以非它莫属啦!
  • 使用mongoDB,可优化订单列表。后台订单经常按照时间查询订单列表。
  • 使用redis,可优化库存管理,以免在秒抢时,出现多用户同时抢到同一商品的情况。

4. 开发架构

系统所需的工程:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
1~/workspace/gitee/high-concurrency on master ⌚ 9:54:01
2$ tree -I target
3.
4├── common            //公共模块 [cn.lilyssh.common]
5├── config-server     //分布式配置中心服务 [cn.lilyssh.config]
6├── goods             //商品服务
7│   ├── goods-api         //实体类和接口定义层 [cn.lilyssh.goods.api]
8│   ├── goods-consumer    //接口访问层 [cn.lilyssh.goods.consumer]
9│   └── goods-provider    //数据访问层 [cn.lilyssh.goods.provider]
10├── order             //订单服务
11│   ├── order-api         //实体类和接口定义层 [cn.lilyssh.order.api]
12│   ├── order-consumer    //接口访问层 [cn.lilyssh.order.consumer]
13│   └── order-provider    //数据访问层 [cn.lilyssh.order.provider]
14└── user              //用户服务
15    ├── user-api          //实体类和接口定义层 [cn.lilyssh.user.api]
16    ├── user-consumer     //接口访问层 [cn.lilyssh.user.consumer]
17    └── user-provider     //数据访问层 [cn.lilyssh.user.provider]
18
19

开发环境:

UTF-8
IDEA
Git
JDK1.8
Maven 3

开发技术选型:

MVC框架:
Spring Boot 2.0.4
Rest接口实现:
Spring MVC Rest
持久层:
mybatisplus-spring-boot 1.0.5
数据库连接池:
druid 1.1.10
分库分表:
mycat
数据库:
MySql 5.6
缓存框架:
Redis、mongoDB
搜索引擎:
Elasticsearch
网关:
Nginx、Kong(纯属学习使用)
API 开发:
swagger
RPC框架:
dubbo-spring-boot 2.0.0
注册中心:
zookeeper
日志管理:
SLF4J
消息队列:
Kafka
分布式配置中心:
spring cloud config
部署:
Jenkins

1).微服务的架构

每个微服务的架构基本上是一致的。拿order来说,分为 order-api、order-consumer、order-provider。


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
1~/workspace/gitee/high-concurrency/order on master ⌚ 11:18:53
2$ tree -I target
3.
4├── order-api
5│   ├── pom.xml
6│   └── src
7│       └── main
8│           └── java
9│               └── cn.lilyssh.order.api
10│                   ├── model
11│                   │   ├── request
12│                   │   │   ├── OrderInsertReq.java
13│                   │   │   └── OrderQueryReq.java
14│                   │   └── response
15│                   │       └── OrderQueryResp.java
16│                   └── service
17│                       └── OrderServiceApi.java
18├── order-consumer
19│   ├── pom.xml
20│   └── src
21│       └── main
22│           ├── java
23│           │   └── cn
24│           │       └── lilyssh
25│           │           └── order
26│           │               └── consumer
27│           │                   ├── OrderConsumerApplication.java
28│           │                   ├── controller
29│           │                   │   └── OrderController.java
30│           │                   └── service
31│           │                       └── OrderService.java
32│           └── resources
33│               ├── application.yml
34│               └── bootstrap.yml
35├── order-provider
36│   ├── pom.xml
37│   └── src
38│       └── main
39│           ├── java
40│           │   └── cn
41│           │       └── lilyssh
42│           │           └── order
43│           │               └── provider
44│           │                   ├── OrderProviderApplication.java
45│           │                   ├── dao
46│           │                   │   ├── entity
47│           │                   │   │   └── OrderEntity.java
48│           │                   │   ├── mapper
49│           │                   │   │   └── OrderMapper.java
50│           │                   │   └── repository
51│           │                   │       └── OrderRepository.java
52│           │                   └── service
53│           │                       └── OrderService.java
54│           └── resources
55│               ├── application.yml
56│               └── bootstrap.yml
57└── pom.xml
58
59
  • api项目 提供 前端与consumer层 以及 consumer层与provider层 进行数据传递的实体类和接口xxServiceApi,实体类分为请求类和响应类,这两个包中又根据不同的业务需求分为不同的实体类。实体和接口访问层虽然属于“层”,但它们并不单独发布,而是使用Jar包类库的方式提供给其它服务调用,是逻辑上的层。其他任意项目可dependency此api模块,并调用此api模块提供的接口。
  • consumer 项目中包含controller层和service层,controller给前端提供rest接口,它调用service的方法,service中写业务逻辑,且调用api模块的接口ServiceApi。
  • provider 项目的主要任务是为api项目的接口xxServiceApi提供实现,即xxService,进行数据访问,分为entity,mapper,repository,entity中存放与数据库表字段一一映射的实体类,用于与数据库进行数据传递的交互。mapper由于继承了mybatisplus的BaseMapper,所以本身提供了增删改查等基本方法,如需自定义方法,可自行添加。repository可对业务逻辑进行进一步的拆解。
  • 配置文件application.yml中存放与其他项目不可公用的配置,如端口,其他公用的配置放在分布式配置中心,bootstrap.yml文件中设置分布式配置中心服务地址,和需要下载的配置文件。由于consumer和provider中都用到了配置文件,所以把这点拿出来单独说。

2).分布式配置中心

我们来看一下配置服务config-server项目的目录结构:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
1~/workspace/gitee/high-concurrency/config-server on master ⌚ 16:10:35
2$ tree -I target
3├── pom.xml
4└── src
5    └── main
6        ├── java
7        │   └── cn
8        │       └── lilyssh
9        │           └── config
10        │               └── ConfigApplication.java
11        └── resources
12            └── application.yml
13
14

application.yml中用来设置配置仓库地址。

3).公用的项目

即common项目的目录结构。common项目主要是放一些工具类、异常的统一捕获处理,还有consumer对前端返回结果的统一封装。


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
1~/workspace/gitee/high-concurrency/common on master ⌚ 16:20:17
2$ tree -I target
3.
4├── pom.xml
5└── src
6    └── main
7        ├── java
8        │   └── cn
9        │       └── lilyssh
10        │           └── common
11        │               ├── date
12        │               │   └──DateUtil.java
13        │               ├── exception
14        │               │   └── ExceptionAdviceHandler.java
15        │               ├── result
16        │               │   ├── Result.java
17        │               │   ├── ReturnCode.java
18        │               │   └── ReturnCodeInterFace.java
19        │               └── validate
20        │                   └── ValidateGroup.java
21        └── resources
22            └── META-INF
23                └── spring.factories
24
25

5. 表结构

用户表:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
1CREATE TABLE `user` (
2  `id` int(11) NOT NULL,
3  `uuid` varchar(45) DEFAULT NULL,
4  `user_name` varchar(20) DEFAULT NULL,
5  `password` varchar(45) DEFAULT NULL,
6  `real_name` varchar(20) DEFAULT NULL,
7  `sex` bit(1) DEFAULT NULL,
8  `age` int(11) DEFAULT NULL,
9  `phone` int(11) DEFAULT NULL,
10  `email` varchar(45) DEFAULT NULL,
11  `status` tinyint(1) DEFAULT NULL,
12  `last_login_ip` varchar(45) DEFAULT NULL,
13  `last_login_time` datetime DEFAULT NULL,
14  `id_type` int(11) DEFAULT NULL,
15  `id_number` varchar(45) DEFAULT NULL,
16  `address` varchar(45) DEFAULT NULL,
17  PRIMARY KEY (`id`)
18) ENGINE=InnoDB DEFAULT CHARSET=utf8;
19
20

订单表:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
1CREATE TABLE `order` (
2  `id` int(11) NOT NULL,
3  `user_id` int(11) DEFAULT NULL,
4  `user_uuid` varchar(45) DEFAULT NULL,
5  `goods_id` int(11) DEFAULT NULL COMMENT '商品ID',
6  `payment` decimal(14,2) DEFAULT NULL COMMENT '实付金额',
7  `pay_type` tinyint(1) DEFAULT NULL COMMENT '支付类型:1 在线支付 2 货到付款',
8  `post_fee` decimal(6,2) DEFAULT NULL,
9  `status` tinyint(2) DEFAULT NULL,
10  `create_time` datetime DEFAULT NULL,
11  `update_time` datetime DEFAULT NULL,
12  `pay_time` datetime DEFAULT NULL,
13  `cosign_time` datetime DEFAULT NULL COMMENT '发货时间',
14  `end_time` datetime DEFAULT NULL COMMENT '交易完成时间',
15  `close_time` datetime DEFAULT NULL COMMENT '交易关闭时间',
16  `shipping_name` varchar(20) DEFAULT NULL COMMENT '物流名称',
17  `shipping_code` varchar(45) DEFAULT NULL COMMENT '物流单号',
18  PRIMARY KEY (`id`)
19) ENGINE=InnoDB DEFAULT CHARSET=utf8;
20
21

商品表:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
1CREATE TABLE `goods` (
2  `id` mediumint(8)  NOT NULL AUTO_INCREMENT,
3  `goods_name` varchar(45) NOT NULL COMMENT '商品名称',
4  `stock` int(11) NOT NULL,
5  `logo` varchar(150) NOT NULL DEFAULT '' COMMENT '商品logo',
6  `sm_logo` varchar(150) NOT NULL DEFAULT '' COMMENT '商品缩略图logo',
7  `price` decimal(10,2) NOT NULL DEFAULT '0.00' COMMENT '商品价格',
8  `goods_desc` longtext COMMENT '商品描述',
9  `is_on_sale` tinyint(3)  NOT NULL DEFAULT '1' COMMENT '是否上架:1:上架,0:下架',
10  `is_delete` tinyint(3)  NOT NULL DEFAULT '0' COMMENT '是否已经删除,1:已经删除 0:未删除',
11  `create_time` int(10)  NOT NULL COMMENT '添加时间',
12  `update_time` int(10)  NOT NULL COMMENT '修改时间',
13  PRIMARY KEY (`id`)
14) ENGINE=InnoDB DEFAULT CHARSET=utf8;
15
16

给TA打赏
共{{data.count}}人
人已打赏
安全经验

Google Adsense广告CPC(单元点击价格)为什么会减少??

2021-10-11 16:36:11

安全经验

安全咨询服务

2022-1-12 14:11:49

个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索