高并发核心编程SpringCloud+Nginx秒杀实战,秒杀系统的系统架构

简介: 秒杀系统的系统架构本节分多个维度介绍crazy-springcloud开发脚手架的架构,包括分层架构、限流架构、分布式锁架构、削峰的架构。秒杀的分层架构从分层的角度来说,秒杀系统架构可以分成3层,大致如下:(1)客户端:负责内容提速和交互控制。(2)接入层:负责认证、负载均衡、限流。(3)业务层:负责保障秒杀数据的一致性。

秒杀系统的系统架构

本节分多个维度介绍crazy-springcloud开发脚手架的架构,包括分层架构、限流架构、分布式锁架构、削峰的架构。

秒杀的分层架构

从分层的角度来说,秒杀系统架构可以分成3层,大致如下:

(1)客户端:负责内容提速和交互控制。

(2)接入层:负责认证、负载均衡、限流。

(3)业务层:负责保障秒杀数据的一致性。

1.客户端负责内容提速和交互控制

客户端需要完成秒杀商品的静态化展示。无论是在桌面浏览器还是在移动端App展示秒杀商品,秒杀商品的图片和文字元素都需要尽可能静态化,尽量减少动态元素。这样就可以通过CDN来提速和抗峰值。

另外,在客户端这一层的用户交互上需要具备一定的控制用户行为和禁止重复秒杀的能力。比如,当用户提交秒杀请求之后,可以将秒杀按钮置灰,禁止重复提交。

2.接入层负责认证、负载均衡、限流

秒杀系统的特点是并发量极大,但实际的优惠商品有限,秒杀成功的请求数量很少,如果不在接入层进行拦截,大量请求就会造成数据库连接耗尽、服务端线程耗尽,导致整体雪崩。因此,必须在接入层进行用户认证、负载均衡、接口限流。

对于总流量较小的系统,可以在内部网关(如Zuul)完成用户认证、负载均衡、接口限流的功能,具体的分层架构如图10-2所示。

网络异常,图片无法展示
|

图10-2 在内部网关(如Zuul)完成认证、负载均衡、接口限流

对于总流量较大的系统会有一层甚至多层外部网关,因此限流的职责会从内部网关剥离到外部网关,内部网关(如Zuul)仍然具备权限认证、负载均衡的能力,具体的分层架构如图10-3所示。

网络异常,图片无法展示
|

图10-3 外部网关与内部网关相结合完成权限认证、负载均衡、接口限 流

3.业务层负责保障数据一致性

秒杀的业务逻辑主要是下订单和减库存,都是数据库操作。大家都知道,数据库层只能承担“能力范围内”的访问请求,既是非常脆弱的一层,又是需要进行事务保护的一层。在业务层还需要防止超出库存的秒杀(超卖和少卖),为了安全起见,可以使用分布式锁对秒杀的数据库操作进行保护。

秒杀的限流架构

前面提到,秒杀系统中的秒杀商品总是有限的。除此之外,服务节点的处理能力、数据库的处理能力也是有限的,因此需要根据系统的负载能力进行秒杀限流。

总体来说,在接入层可以进行两个级别的限流策略:应用级别的限流和接口级别的限流。

什么是应用级别的限流策略呢?对于整个应用系统来说,一定会有一个QPS的极限值,如果超了极限值,整个应用就会不响应或响应得非常慢。因此,需要在整个应用的维度做好应用级别的限流配置。应用级别的限流应该配置在最顶层的反向代理,具体如图10-4所示。

网络异常,图片无法展示
|

图10-4 应用级别的限流

应用级别的流量限制可以通过Nginx的limit_req_zone和limit_req两个指令完成。假定要配置Nginx虚拟主机的限流规则为单IP限制为每秒1次请求,整个应用限制为每秒10次请求,那么具体的配置如下:

limit_req_zone $binary_remote_addr zone=perip:10m rate=1r/s;
limit_req_zone $server_name zone=perserver:1m rate=10r/s;
server {
 ...
 limit_req zone=perip burst=5;
 limit_req zone=perserver burst=10;
}

什么是接口级别的限流策略呢?单个接口可能会有突发访问情况,可能会由于突发访问量太大造成系统崩溃,典型的就是本章所介绍的秒杀类接口。接口级别的限流就是配置单个接口的请求速率,是细粒度的限流。

接口级别的限流也可以通过Nginx的limit_req_zone和limit_req两个指令配合完成,对获取秒杀令牌的接口,同时进行用户Id和商品Id限流的配置如下:

limit_req_zone $arg_goodId zone=pergood:10m rate=100r/s;
limit_req_zone $arg_userId zone=peruser:1m rate=1r/s;
server {
 #lua:获取秒杀token令牌
 location = /seckill-provider/api/seckill/redis/token/v2 {
 limit_req zone=peruser burst=5;
 limit_req zone=pergood burst=10;
 #获取秒杀token lua脚本
 content_by_lua_file luaScript/module/seckill/getToken.lua;
 }
}

以上定义了两个限流规则:pergood和peruser:pergood规则根据请求参数的goodId值进行限流,同一个goodId值的限速为每秒100次请求;peruser规则根据请求参数的userId值进行限流,同一个userId值的限速为每秒1次请求。

但是,Nginx的限流指令只能在同一块内存区域有效,而在生产场景中秒杀的外部网关往往是采用多节点部署的,所以这就需要用到分布式限流组件。高性能的分布式限流组件可以使用Redis+Lua来开发,京东的抢购就是使用Redis+Lua完成限流的,并且无论是Nginx外部网关还是Zuul内部网关,都可以使用Redis+Lua限流组件。

理论上,接入层的限流有多个维度:

(1)用户维度的限流:在某一时间段内只允许用户提交一次请求,比如可以采取客户端IP或者用户ID作为限流的key。

(2)商品维度的限流:对于同一个抢购商品,在某个时间段内只允许一定数量的请求进入,可以采取秒杀商品ID作为限流的key。

无论是哪个维度的限流,只要掌握其中的一个,其他维度的限流在技术实现上都是差不多的。本书的秒杀练习使用的是接口级别的限流策略,在获取秒杀令牌的REST接口时,针对每个秒杀商品的ID配置限流策略,限制每个商品ID每秒内允许通过的请求次数。

如果大家对进行用户维度的限流感兴趣,可以自行修改配置进行尝试。

秒杀的分布式锁架构

前面提到了超卖或少卖问题:比如10万次请求同时发起秒杀请求,正常需要进行10万次库存扣减,但是由于某种原因,往往会造成多减库存或者少减库存,这就会出现超卖或少卖问题。

解决超卖或者少卖问题有效的办法之一就是利用分布式锁将对同一个商品的并行数据库操作予以串行化。秒杀场景的分布式锁应该具备如下条件:

(1)一个方法在同一时间只能被一个机器的一个线程执行。

(2)高可用地获取锁与释放锁。

(3)高性能地获取锁与释放锁。

(4)具备可重入特性。

(5)具备锁失效机制,防止死锁。

(6)具备非阻塞锁特性,即没有获取到锁将直接返回获取锁失败。

常用的分布式锁有两种:ZooKeeper分布式锁和Redis分布式锁。如果使用ZooKeeper分布式锁来保护秒杀的数据库操作,那么它的架构图大致如图10-5所示。

网络异常,图片无法展示
|

图10-5 使用ZooKeeper分布式锁来保护秒杀的数据库操作

实际上,除了提供分布式锁外,ZooKeeper还能提供高可靠的分布式计数器、高可靠的分布式ID生成器的基础能力。ZooKeeper分布式计数器、分布式锁、分布式ID生成器等基础知识也是大家必须系统地学习和掌握的知识,但是不属于在本书介绍的内容,如果对这一块不了解,可翻阅本书姊妹篇《Netty、Redis、ZooKeeper高并发实战》。

ZooKeeper分布式锁虽然高可靠,但是性能不高,不能满足秒杀场景分布式锁的第3个条件(高性能地获取锁与释放锁),所以在秒杀的场景建议使用Redis分布式锁来保护秒杀的数据库操作。

秒杀的削峰架构

通过接入网关的限流能够拦截无效的刷单请求和超出预期的那部分请求,但是,当秒杀的订单量很大时,比如有100万商品需要参与秒杀,这时后端服务层和数据库的并发请求压力至少为100万。这种请求下,需要使用消息队列进行削峰。

削峰从本质上来说就是更多地延缓用户请求,以及层层过滤用户的访问需求,遵从“最后落地到数据库的请求数要尽量少”的原则。通过消息队列可以大大地缓冲瞬时流量,把同步的直接调用转换成异步的间接推送,中间通过一个队列在入口承接瞬时的流量洪峰,在出口平滑地将消息推送出去。消息队列就像“水库”一样,拦蓄上游的洪水,削减进入下游河道的洪峰流量,从而达到减免洪水灾害的目的。使用消息队列对秒杀进行削峰的架构如图10-6所示。

网络异常,图片无法展示
|

图10-6 使用消息队列对秒杀进行削峰

对于秒杀消息的入队可以直接在内部网关完成。内部网关在完成用户的权限验证、秒杀令牌的有效性验证之后,将秒杀消息发往消息队列即可。秒杀服务通过消息队列的订阅完成秒杀消息的消费。常用消息队列系统:Kafka、RocketMQ、ActiveMQ、RabbitMQ、ZeroMQ、MetaMQ等。本书的内容主要聚焦在Spring Cloud和Nginx,对消息队列这里不做过多的介绍,使用消息队列进行削峰的秒杀实现版本可参见后续的疯狂创客圈社群博客。

本文给大家讲解的内容是高并发核心编程,Spring Cloud+Nginx秒杀实战,秒杀系统的系统架构

相关文章
|
4月前
|
人工智能 算法 前端开发
超越Prompt Engineering:揭秘高并发AI系统的上下文工程实践
本文系统解析AI工程范式从Prompt Engineering到Context Engineering的演进路径,深入探讨RAG、向量数据库、上下文压缩等关键技术,并结合LangGraph与智能体系统架构,助力开发者构建高可靠AI应用。
646 2
|
6月前
|
缓存 NoSQL 算法
高并发秒杀系统实战(Redis+Lua分布式锁防超卖与库存扣减优化)
秒杀系统面临瞬时高并发、资源竞争和数据一致性挑战。传统方案如数据库锁或应用层锁存在性能瓶颈或分布式问题,而基于Redis的分布式锁与Lua脚本原子操作成为高效解决方案。通过Redis的`SETNX`实现分布式锁,结合Lua脚本完成库存扣减,确保操作原子性并大幅提升性能(QPS从120提升至8,200)。此外,分段库存策略、多级限流及服务降级机制进一步优化系统稳定性。最佳实践包括分层防控、黄金扣减法则与容灾设计,强调根据业务特性灵活组合技术手段以应对高并发场景。
1790 7
|
7月前
|
应用服务中间件 Linux 网络安全
技术指南:如何把docsify项目部署到基于CentOS系统的Nginx中。
总结 与其他部署方法相比,将docsify项目部署到基于CentOS系统的Nginx中比较简单。以上步骤应当帮助你在不花费太多时间的情况下,将你的项目顺利部署到Nginx中。迈出第一步,开始部署你的docsify项目吧!
327 14
|
缓存 负载均衡 安全
Nginx常用基本配置总结:从入门到实战的全方位指南
Nginx常用基本配置总结:从入门到实战的全方位指南
1150 0
|
6月前
|
负载均衡 Java API
基于 Spring Cloud 的微服务架构分析
Spring Cloud 是一个基于 Spring Boot 的微服务框架,提供全套分布式系统解决方案。它整合了 Netflix、Zookeeper 等成熟技术,通过简化配置和开发流程,支持服务发现(Eureka)、负载均衡(Ribbon)、断路器(Hystrix)、API网关(Zuul)、配置管理(Config)等功能。此外,Spring Cloud 还兼容 Nacos、Consul、Etcd 等注册中心,满足不同场景需求。其核心组件如 Feign 和 Stream,进一步增强了服务调用与消息处理能力,为开发者提供了一站式微服务开发工具包。
657 0
|
Java 开发者 微服务
从单体到微服务:如何借助 Spring Cloud 实现架构转型
**Spring Cloud** 是一套基于 Spring 框架的**微服务架构解决方案**,它提供了一系列的工具和组件,帮助开发者快速构建分布式系统,尤其是微服务架构。
1046 70
从单体到微服务:如何借助 Spring Cloud 实现架构转型
|
8月前
|
人工智能 缓存 NoSQL
高并发秒杀系统设计:关键技术解析与典型陷阱规避
在电商、在线票务等场景中,高并发秒杀活动对系统性能和稳定性提出极大挑战。海量请求可能导致服务器资源耗尽、数据库锁争用及库存超卖等问题。通过飞算JavaAI生成的Redis + Lua分布式锁代码,可有效解决高并发下的锁问题,提升系统QPS达70%,同时避免缓存击穿与库存超卖。相较传统写法,AI优化代码显著提高性能与响应速度,为高并发系统开发提供高效解决方案。
|
12月前
|
存储 JavaScript 开发工具
基于HarmonyOS 5.0(NEXT)与SpringCloud架构的跨平台应用开发与服务集成研究【实战】
本次的.HarmonyOS Next ,ArkTS语言,HarmonyOS的元服务和DevEco Studio 开发工具,为开发者提供了构建现代化、轻量化、高性能应用的便捷方式。这些技术和工具将帮助开发者更好地适应未来的智能设备和服务提供方式。
基于HarmonyOS 5.0(NEXT)与SpringCloud架构的跨平台应用开发与服务集成研究【实战】
|
10月前
|
传感器 监控 安全
智慧工地云平台的技术架构解析:微服务+Spring Cloud如何支撑海量数据?
慧工地解决方案依托AI、物联网和BIM技术,实现对施工现场的全方位、立体化管理。通过规范施工、减少安全隐患、节省人力、降低运营成本,提升工地管理的安全性、效率和精益度。该方案适用于大型建筑、基础设施、房地产开发等场景,具备微服务架构、大数据与AI分析、物联网设备联网、多端协同等创新点,推动建筑行业向数字化、智能化转型。未来将融合5G、区块链等技术,助力智慧城市建设。
527 1
|
11月前
|
搜索推荐 NoSQL Java
微服务架构设计与实践:用Spring Cloud实现抖音的推荐系统
本文基于Spring Cloud实现了一个简化的抖音推荐系统,涵盖用户行为管理、视频资源管理、个性化推荐和实时数据处理四大核心功能。通过Eureka进行服务注册与发现,使用Feign实现服务间调用,并借助Redis缓存用户画像,Kafka传递用户行为数据。文章详细介绍了项目搭建、服务创建及配置过程,包括用户服务、视频服务、推荐服务和数据处理服务的开发步骤。最后,通过业务测试验证了系统的功能,并引入Resilience4j实现服务降级,确保系统在部分服务故障时仍能正常运行。此示例旨在帮助读者理解微服务架构的设计思路与实践方法。
718 17