MySQL 高并发场景实战|学习笔记

简介: 快速学习 MySQL 高并发场景实战。

开发者学堂课程【MySQL 实战进阶MySQL 高并发场景实战】学习笔记,与课程紧密联系,让用户快速学习知识。

课程地址:https://developer.aliyun.com/learning/course/852/detail/14060


MySQL 高并发场景实战

 

内容介绍:

一、问题和挑战

二、系统调优

三、流程管理和生态工具

 

一、问题和挑战

阿里巴巴 CEO 逍遥子说双11是商业界的奥林匹克”。

image.png 

双11从2009年开始举办,从图中可以看到每一年的交易额、支付笔数和订单创建几乎都是翻倍增长的,不但给商业界提供了大炼金的机会,相应的给后端的技术、架构,以及各个模块等等都是比较好的技术沉淀。

在双11面临哪些问题和挑战呢?今天的主题是 MySQL 高并发场景的问题和挑战,这个并发不仅是高并发,而且是洪峰般地并发。

1、洪峰般地并发

根据市场部部门的推广和引流、历年双11的经验,大促的起始时刻呈现接近90度上升趋势。在这么大访问流量下,所有的核心链路的增删改查都是在数据库上操作,对数据库有比较大的冲击,在大量线程并发工作时线程调度工作过多、大量缓存失效、资源竞争加剧、锁冲突严重,如果有复杂 SQL 或大事务的话还可能导致系统资源耗尽,整个数据库服务不可用,进而导致大促受到影响,甚至失败,比如:下单失败、网页无法打开、无法支付等。此外此类场景也会发生在在线教育、直播电商、在线协同办公等。

2、热点行更新

库存扣减场景是一-个典型的热点问题,当多个用户去争抢扣减同一个商品的库存(对数据库来说,一个商品的库存就是数据库内的一行记录),数据库内对同一行的更新由行锁来控制并发。当单线程(排队)去更新一行记录时,性能非常高,但是当非常多的线程去并发更新一行记录时,整个数据库的性能会跌到趋近于零。

3、突发 SQL 访问

当缓存穿透或异常调用、有数据倾斜 SQL、未创建索引 SQL 等情况发生时,在高并发场景下很容易导致数据库压力过大,响应过慢,导致应用链接释放慢,导致整个系统不可用。

4、智能化运维

双十一期间这些实例的水位管控,机器水位管控,高风险实例识别,高风险实例优化,在流量高峰期从收到报警、识别问题、解决问题至少需要十多分钟,如果处理不及时峰值已经过去,导致大促失败。

此外还有商品超卖、资源的挑战等等。

 

二、系统调优

1、容量评估

(1)经验评估

预估压力/单机性能=服务器数量

根据服务器的数量和应用机器的数量、deb 机器的数量,可以得出整个数据库的连接池的设置、扩充的实例、扩充的应用机器等等,这些配置也会相应出来。

(2)单元压测

需要针对对单个实例、单个单元、单个应用模块进行压测,单元压测的主要功能是完成单元内的验证,不光是验证整个双11的流量,还要验证在单元内这个容量是否充足,以及单个系统的容量,比如是压测某一个模块(交易模块、优惠模块等等)。

(3)全链路压测

基于场景化的仿真测试,这是最接近业务的系统值的,针对全链路压测可以借助压测来验证整个分布式系统容量是否充足。

2、性能评测

(1)压测目的

发现基础设施瓶颈、中间件瓶颈系统容量瓶颈是否充足

发现分布式系统短板

(2)压测用途

保障大促容量充足,保障业务正常运转

保障核心功能、保证用户体验

评估大促成本

(3)难点

真实业务场景压测

真实 SQL 模拟

(4)基准测试

image.png

基准测试可以用 sysbenchmysqlslap 等等,官网上有基于通用场景的测试,每一个实例所达到的容量在不同的业务场景下是不一样的,通过基准测试可以预估实例所能达到的最大值、极限值,通常情况下真实的业务场景不大可能超过基准业务的值的,所以针对每一个实例所能达到的瓶颈做到心中有数。

(5)全链路压测——大促备战核武器

真实业务场景的压测往往比基准测试要复杂,阿里在双11的场景下是如何压测的呢?整个过程大概可以分为4个步骤。

首先,针对基础的涉及到的业务模块进行梳理,相应也会梳理技术架构模块以及容量预估是否充足。梳理完成之后需要造数据,准备服务器、压测流量、业务请求。

第三步进入正式压测阶段,通过压测发现短板,验证容量是否充足,验证预案。验证压测执行完成后需要针对发现的短板问题、容量问题、架构问题进行针对性的优化。

这个过程不是一蹴而就的,而是要经过很多轮的压测,阿里巴巴集团及各 BU 每年压测4000+次,每一年通过全链路发现几百个线上在以前的测试过程中没有发现的问题,所以这个真实的业务场景压测已经成为双11的必备阶段,是大促准备的备战核武器

(6)工具

PTS(Performance Testing Service)是面向所有技术背景人员的云化测试工具。有别于传统工具的繁复,PTS 以互联网化的交互,提供性能测试、API 调试和监测等多种能力。自研和适配开源的功能都可以轻松模拟任意体量的用户访问业务的场景,任务随时发起,免去繁琐的搭建和维护成本。

更是紧密结合监控、流控等兄弟产品提供站式高可用能力高效检验和管理业务性能。

DAS(Database Autonomy Service)智能压测主要应用在以下两种场景

●为应对即将到来的短期业务高峰验证当前的 RDS MySQL 规格是否需要扩容。

●数据库迁移上云前,验证目标 RDS MySQL 的规格是否满足业务需求。

(7)注意

●参数的对齐

如果想对比两个参数,在打开和关闭之后,以及设置不同的值对性能的影响,可以单独做测试。一旦测试出来最优,在压缩之前最好把参数调到最优值,不要等到压缩出来有问题了再来调参数

●网络

一般情况下,购买实例的时候 ECS  RDS 是在同一个 VBC的,但是排除用户拿线下的用的机器链接本地的数据库,然后拿本地的应用机器链接 RDS 来做性能对比,这种就是不合适的,一个主要的原因就是压测机 RDS 的网络延迟和到本地数据库的延迟差异很大

●规格

不同 RDS 的规格,它的性能差别比较大的,如果想测试 CPU 的性能,物理 IO要少,数据在内存里,但是大多数业务场景都是涉及到物理 IO 的,所以到测试数据的时候,数据量要大于内存的大小

●ECS 的网络带宽

阿里云的 ECS 限制网络带宽,以往有用户做测试的时候,RDS 资源都没有用满,但是压力也上不去,后来经过定位使 ECS 的网络带宽打满了,所以在准备整个压测的环境时,要把这些内容调好。

3、架构调优

针对数据库来说,如果所有业务的访问都用数据库来支撑,这个成本太高了

首先是缓存,它可以代替一部分关系型数据库在读方面的请求,此外,基于原理的设计以及成本方面来考虑缓存的独特性能是要比关系型数据库要好的,在成本方面也是性价比是比较高的

到数据库层面,如果要是读多写少,针对单个实例很难支撑,还可以借助于只读实例只读实例可以实现在线性的扩展读能力读的业务请求可以实现隔离,比如说可以把轻分析型拖数据型在只读实例内完成

此外,每一个只读实例都有一个单独的链接地址,如果想把某一类的业务和其他的业务区分开严格的隔离,比如说让拖数据类的场景,或者是某一类的只读的场景,某一个实例上面来访问,就可以单独的链接那个只读实例的链接串,但是如果想从整个层面来控制主实和只读实例的访问,可以借助于负载均衡独享代理来完成

独享代理可以缓解大量的短链接的场景,使用代理后不用反复的变更用内的链接地址,减少维护成本,可以对线上的资源实现扩展,承受更高的流量如果 RDS 的实例规格以及只读实例都已经升到最大,但仍然不能支撑业务的发展,可以考虑把 RDS 升级到 Polar MySQL,或者是 PolarX 2.0这种方式来完成读写容量上面的扩展

刚才提到只读实例,其实大家最关心的一个问题就是主实例和只读实例的数据一致性,比如说有延迟以及中断的这一类的场景的延迟是最多的,针对线上的延迟的问题,我们做了一个分析,主要原因包括5个方面:

●主实例的 DDL

占40%,如 alterdrop 等。需要 kill DDL 语句或用 DMS 的无锁变更等。

●主实例的大事务

占20%,如大批量导入、删除、更新数据。需要将大事务拆分成为小事务进行批量提交这样只读节点就可以迅速的完成事务的执行,不会造成数据的延迟。

●主实例写入压力过大

占20%,如主实例规格较小压力过大。这种情况需要升级主实例和只读实例的规格。

●只读节点规格过小

占10%,这种情况升级只读实例规格。

●其他(无主键)

占10%,RDS目前已经支持对表添加隐式主键,但是对于以前历史创建的表需要进行重建才能支持隐式主键。

刚才提到缓存,在高并发场景下,写入压力过大,怎样提升缓存命中率?根据以往的经验,有4种更新方式:Cache aside,Read through,Write through,Write behind caching。缓存的更新、应用可以从 Cache 里读取数据,取到后返回,或者没有取,从数据库里取,成功后再返回缓存中。Read through 是没有读到后更新缓存。Write through 是在数据更新时,发现缓存里没有,就更新缓存。Write back 类似于底层的操作系统的机制,它可以合并同一个数据的多次操作以上几种方式都不能保证版权命中率那如何保证版权命中率呢?做核心系统的时候,有一个小巧思,

image.png

就是应用程序把写请求到 RDS,读请求到 Redis,RDS 的变更数据底层是通过数据变更的这种方式,拿到增量数据后,更新 Redis,这是一个小巧思。它的好处是:

更新路径短,延迟低

缓存失效为异步流程,业务更新 DB 完成后直接返回,不需要关心缓存失效流程,整个更新路径短,更新延迟低。

应用简单可靠

应用无需实现复杂双写逻辑,只需启动异步线程监听增量数据,更新缓存数据即

可。

应用更新无额外性能消耗

因为数据订阅是通过解析 DB 的增量日志来获取增量数据,获取数据的过程对业务、DB 性能无损。

4、实例调优

(1)弹性扩容

 image.png

(2)参数调优

影响性能的几个主要参数:

●和连接相关的几个参数

back_ log  标记 MySQL 的并发链接数

table_ open_ cache  所有线程打开表的数量

thread_ cache_ size  

loose_ thread_ pool_ enabled

●和 IO 相关的几个参数

sync_ binlog

innodb_ fush_ logs_ at _trx _ commit

innodb_ io_ capacity

innodb_ io_ capacity_ max

●和内存相关的几个参数

innodb_ buffer _pool_ instances

join_ buffer_ size

tmp_ table_ size

我们把我们认为是对性的影响比较大的参数调整到高性能模板里面,应用时就可以找到对应的参数,应用到对应的实例。下图是根据普通模板以及高性能模板做的一个对比,我们可以看到普通模板相比高性能模板要低25%左右的性能。

image.png

5、内核调优

(1)版本升级

image.png

从版本上来讲,现在官方维护的是5.65.7和8.0,每一个版本的升级会带来一些新的特性,同时,它的性能也会上升,从表里可以看到8.0的性能是最强的,但是升级时也会一些坑,比如执行计划有些和原来的版本不太兼容。

(2)AliSQL 特性

最开始讲了高并发场景下面临的挑战,也会针对这些挑战提供解决方案,针对高并发的场景以及热点库存的场景,AliSQL 提供了四个补丁,其中三个补丁针对热点库存更新,其中一个补丁是库存注释。

库存注释在秒杀业务场景中,减库存场景包含两个从业务逻辑上来讲,包括拍下减库存和付款减库存。拍下减库存就是在客户拍下的时候把库存减掉,业务逻辑比较简单。付款减库存的业务逻辑比较复杂,在用户付完款后才减库存,因为复杂所以一条语句不能完成,是在事务里完成的,行锁冲突本来就比较严重,如何才能提升事务里的性能,通常情况下,开启和结束事务都是由应用来完成,如果应用处理的过慢或者网络交互的时间过慢、网络拥堵,它会增加它所持有的时间。

库存注释把持有行锁的时间、行锁释放交给数据库自己来做,AliSQL 使用排队和事务性 hint 成功就提交,失败就回滚,把控制权交给 MySQL 内核,这样可以减少行锁持有的时间,快速结束事务,进而提高减库存的吞吐能力

在减库存场景里,MySQL 分为引擎层和 server ,在高并发场景下,同一行的行锁会在 server 、引擎层来回切换,InnoDB 中事务锁的最细粒度是行级锁,如果语句针对相同行进行并发操作,会导致冲突比较严重,所以 AliSQL 把这个冲突放在 server 进行排队,对于相同行的冲突在一个桶内,可以减少冲突检测的开销,进而减少引擎层、server 来回切换带来的消耗。

第三个是语句返回,这个特性在 PG 里有,更新完后直接将结果返回,但是 MySQL 是没有的,AliSQL 把这个特性吸纳进来后也带有这个特性,如果在一个事务里更新完一行记录后,应用再发起 select,这条结果再返回给应用,可以看到它会多一次网络交互。

如果直接把 abdata 的结果返回就可以减少这次网络交互,有多次的时候性能提升可以节省多次的网络交互和应用判断的时间,也可以带来事务的性能提升以及应用性能的提升。

对于高并发场景下,AliSQL 是用线程池解决的,线程池在有大量线程来并发访问的时候,线程池会自动调节并发的线程数量在合理的范围内,避免线程池过多造成的大量缓存失效。

还有在高并发场景下,线程池会语句和事务分为不同的优先级,分别控制语句和事务的并发数量,减少资源竞争,线程池也会根据不同语句的复杂性来控制它的优先级,所以使用线程池可以将不同的 SQL 控制在合理的连接数的范围,使数据库在大的场景下保持高性能

下图是用库存注释、语句队列做的性能对比:

image.png

和原生的相比,已经翻了40倍。

6、监控报警

系统调优必不可少监控,有 RDS 自带的监控资源层的监控、引擎层的监控,还有日志的监控

对于收费来说,包括审计日志以及自服务会基于上面的 RDS 自带的以及审计日志会做一些分析,在这个基础上做的一些报警,此外,还有分布式的监控可以监控在不同的组件里面,它的瓶颈在哪里 

 

三、流程管理和生态工具

基于生态工具的保障可以从变更的流程、稳定性和数据恢复三方面来管理、介绍。

1、变更流程
image.png 

在大促期间,可以有很好的流程来提升稳定性,这个是增加在审批环节来增加审批的流程,稳定性相关的不要因为人为的因素给系统造成压力,可以设置通过 DMS 来执行的 SQL,不要让它超过一定的时间,也可以针对某一类的 DDL 或者是 DML 不允许执行,可以设置安全规则。

image.png

内核的特性,有的用户他会在业务高峰的时候会进行大文件的删除,会造成文件系统的 hint进而影响数据库的稳定性,可能会造成数据库的抖动

针对这个特性特点,阿里 SQL 提供这样的一个补丁,可以提供小批量的异步删除,慢慢的删,来减少、降低,甚至没有,取决于每一次设置的清理大小。

 image.png

还有并发的 SQL 访问,当有缓存失效或者是有数据倾斜,或者是未创建索引 SQL 的时候,会造成数据库压力过大。

阿里 SQL 针对这一类的 SQL 做了并发控制的补丁,根据关键词识别出来之后可以控制这一类 SQL 的并发度并发执行,最多允许执行多少,防止某一类的 SQL 把系统打卡的风险。

2、数据恢复

image.png

image.png

从数据恢复上来说,有的用户一般在大促的时候甚至在高峰的时候人肉来做一些数据的变更万一数据变更条件写错,也可以通过数据追踪来恢复

image.png

数据恢复还可以通过备份来恢复,备份可以分为克隆实例、整个实例级别的恢复以及库/表级别的恢复,还可以通过 DBS 数据库备份来恢复

相关实践学习
每个IT人都想学的“Web应用上云经典架构”实战
本实验从Web应用上云这个最基本的、最普遍的需求出发,帮助IT从业者们通过“阿里云Web应用上云解决方案”,了解一个企业级Web应用上云的常见架构,了解如何构建一个高可用、可扩展的企业级应用架构。
MySQL数据库入门学习
本课程通过最流行的开源数据库MySQL带你了解数据库的世界。   相关的阿里云产品:云数据库RDS MySQL 版 阿里云关系型数据库RDS(Relational Database Service)是一种稳定可靠、可弹性伸缩的在线数据库服务,提供容灾、备份、恢复、迁移等方面的全套解决方案,彻底解决数据库运维的烦恼。 了解产品详情: https://www.aliyun.com/product/rds/mysql 
相关文章
|
5月前
|
缓存 关系型数据库 MySQL
在MySQL中处理高并发和负载峰值的关键技术与策略
采用上述策略和技术时,每个环节都要进行细致的规划和测试,确保数据库系统既能满足高并发的要求,又要保持足够的灵活性来应对各种突发的流量峰值。实施时,合理评估和测试改动对系统性能的影响,避免单一措施可能引起的连锁反应。持续的系统监控和分析将对维护系统稳定性和进行未来规划提供重要信息。
315 15
|
6月前
|
缓存 监控 Cloud Native
Java Solon v3.2.0 高并发与低内存实战指南之解决方案优化
本文深入解析了Java Solon v3.2.0框架的实战应用,聚焦高并发与低内存消耗场景。通过响应式编程、云原生支持、内存优化等特性,结合API网关、数据库操作及分布式缓存实例,展示其在秒杀系统中的性能优势。文章还提供了Docker部署、监控方案及实际效果数据,助力开发者构建高效稳定的应用系统。代码示例详尽,适合希望提升系统性能的Java开发者参考。
362 4
Java Solon v3.2.0 高并发与低内存实战指南之解决方案优化
|
6月前
|
关系型数据库 MySQL 分布式数据库
Super MySQL|揭秘PolarDB全异步执行架构,高并发场景性能利器
阿里云瑶池旗下的云原生数据库PolarDB MySQL版设计了基于协程的全异步执行架构,实现鉴权、事务提交、锁等待等核心逻辑的异步化执行,这是业界首个真正意义上实现全异步执行架构的MySQL数据库产品,显著提升了PolarDB MySQL的高并发处理能力,其中通用写入性能提升超过70%,长尾延迟降低60%以上。
|
6月前
|
缓存 NoSQL 算法
高并发秒杀系统实战(Redis+Lua分布式锁防超卖与库存扣减优化)
秒杀系统面临瞬时高并发、资源竞争和数据一致性挑战。传统方案如数据库锁或应用层锁存在性能瓶颈或分布式问题,而基于Redis的分布式锁与Lua脚本原子操作成为高效解决方案。通过Redis的`SETNX`实现分布式锁,结合Lua脚本完成库存扣减,确保操作原子性并大幅提升性能(QPS从120提升至8,200)。此外,分段库存策略、多级限流及服务降级机制进一步优化系统稳定性。最佳实践包括分层防控、黄金扣减法则与容灾设计,强调根据业务特性灵活组合技术手段以应对高并发场景。
1801 7
|
5月前
|
数据采集 监控 网络协议
基于aiohttp的高并发爬虫实战:从原理到代码的完整指南
在数据驱动时代,传统同步爬虫效率低下,而基于Python的aiohttp库可构建高并发异步爬虫。本文通过实战案例解析aiohttp的核心组件与优化策略,包括信号量控制、连接池复用、异常处理等,并探讨代理集成、分布式架构及反爬应对方案,助你打造高性能、稳定可靠的网络爬虫系统。
379 0
|
11月前
|
存储 关系型数据库 MySQL
MySQL索引学习笔记
本文深入探讨了MySQL数据库中慢查询分析的关键概念和技术手段。
735 81
|
8月前
|
SQL 安全 测试技术
2025接口测试全攻略:高并发、安全防护与六大工具实战指南
本文探讨高并发稳定性验证、安全防护实战及六大工具(Postman、RunnerGo、Apipost、JMeter、SoapUI、Fiddler)选型指南,助力构建未来接口测试体系。接口测试旨在验证数据传输、参数合法性、错误处理能力及性能安全性,其重要性体现在早期发现问题、保障系统稳定和支撑持续集成。常用方法包括功能、性能、安全性及兼容性测试,典型场景涵盖前后端分离开发、第三方服务集成与数据一致性检查。选择合适的工具需综合考虑需求与团队协作等因素。
1291 24
|
存储 关系型数据库 MySQL
MySQL在企业内部应用场景有哪些
【10月更文挑战第17天】MySQL在企业内部应用场景有哪些
575 0
|
9月前
|
消息中间件 NoSQL 关系型数据库
去哪面试:1Wtps高并发,MySQL 热点行 问题, 怎么解决?
去哪面试:1Wtps高并发,MySQL 热点行 问题, 怎么解决?
去哪面试:1Wtps高并发,MySQL 热点行 问题, 怎么解决?
|
缓存 NoSQL Java
高并发场景秒杀抢购超卖Bug实战重现
在电商平台的秒杀活动中,高并发场景下的抢购超卖Bug是一个常见且棘手的问题。一旦处理不当,不仅会引发用户投诉,还会对商家的信誉和利益造成严重损害。本文将详细介绍秒杀抢购超卖Bug的背景历史、业务场景、底层原理以及Java代码实现,旨在帮助开发者更好地理解和解决这一问题。
397 12

推荐镜像

更多