0

0

MySQL主从延迟、读写分离的解决方法总结

WBOY

WBOY

发布时间:2022-05-26 11:53:52

|

2010人浏览过

|

来源于CSDN

转载

本篇文章给大家带来了关于mysql的相关知识,其中主要介绍了关于主从延迟和读写分离的解决方法,下面一起来看一下总结了几个方法,希望对大家有帮助。

MySQL主从延迟、读写分离的解决方法总结

推荐学习:mysql视频教程

我们都知道互联网数据有个特性,大部分场景都是 读多写少,比如:微博、微信、淘宝电商,按照 二八原则,读流量占比甚至能达到 90%

结合这个特性,我们对底层的数据库架构也会做相应调整。采用 读写分离

处理过程:

  • 客户端会集成 SDK,每次执行 SQL 时,会判断是  或  操作

  • 如果是  SQL,请求会发到 主库

  • 主数据库执行SQL,事务提交后,会生成 binlog ,并同步给 从库

  • 从库 通过 SQL 线程回放 binlog ,并在从库表中生成相应数据

  • 如果是  SQL,请求会通过 负载均衡 策略,挑选一个 从库 处理用户请求

看似非常合理,细想却不是那么回事

主库 与 从库 是采用异步复制数据,如果这两者之间数据还没有同步怎么办?

主库刚写完数据,从库还没来得及拉取最新数据, 请求就来了,给用户的感觉,数据丢了???

针对这个问题,今天,我们就来探讨下有什么解决方案?

一、强制走主库

针对不用的业务诉求,区别性对待

场景一:

如果是对数据的 实时性 要求不是很高,比如:大V有千万粉丝,发布一条微博,粉丝晚几秒钟收到这条信息,并不会有特别大的影响。这时,可以走 从库

场景二:

如果对数据的 实时性 要求非常高,比如金融类业务。我们可以在客户端代码标记下,让查询强制走主库。

二、从库延迟查询

由于主从库之间数据同步需要一定的时间间隔,那么有一种策略是延迟从从库查询数据。

比如:

select sleep(1)
select * from order where order_id=11111;

在正式的业务查询时,先执行一个sleep 语句,给从库预留一定的数据同步缓冲期。

因为是采用一刀切,当面对高并发业务场景时,性能会下降的非常厉害,一般不推荐这个方案。

三、判断主从是否延迟?决定选主库还是从库

方案一:

在从库 执行 命令 show slave status

查看 seconds_behind_master 的值,单位为秒,如果为 0,表示主备库之间无延迟

方案二:

比较主从库的文件点位

还是执行 show slave status,响应结果里有截个关键参数

  • Master_Log_File   读到的主库最新文件

  • Read_Master_Log_Pos 读到的主库最新文件的坐标位置

  • Relay_Master_Log_File 从库执行到的最新文件

  • Exec_Master_Log_Pos 从库执行到的最新文件的坐标位置

两两比较,上面的参数是否相等

方案三:

比较 GTID 集合

  • Auto_Position=1   主从之间使用 GTID 协议

    Typeface
    Typeface

    AI创意内容创作助手

    下载
  • Retrieved_Gtid_Set 从库收到的所有binlog日志的 GTID 集合

  • Executed_Gtid_Set 从库已经执行完成的 GTID 集合

比较 Retrieved_Gtid_Set 和 Executed_Gtid_Set 的值是否相等

在执行业务SQL操作时,先判断从库是否已经同步最新数据。从而决定是操作主库,还是操作从库。

缺点:

无论采用上面哪一种方案,如果主库的写操作频繁不断,那么从库的值永远跟不上主库的值,那么读流量永远是打在了主库上。

针对这个问题,有什么解决方案?

这个问题跟 MQ消息队列 既要求高吞吐量又要保证顺序是一样的,从全局来看确实无解,但是缩小范围就容易多了,我们可以保证一个分区内的消息有序。

回到 主从库 之间的数据同步问题,从库查询哪条记录,我们只要保证之前对应的写binglog已经同步完数据即可,可以不用管主从库的所有的事务binlog 是否同步。

问题是不是一下简单多了

四、从库节点判断主库位点

在从库执行下面命令,返回是一个正整数 M,表示从库从参数节点开始执行了多少个事务

select master_pos_wait(file, pos[, timeout]);
  • file 和 pos 表示主库上的文件名和位置

  • timeout 可选, 表示这个函数最多等待 N 秒

缺点:

master_pos_wait 返回结果无法与具体操作的数据行做关联,所以每次接收读请求时,从库还是无法确认是否已经同步数据,方案实用性不高。

五、比较 GTID

执行下面查询命令

  • 阻塞等待,直到从库执行的事务中包含 gtid_set,返回 0

  • 超时,返回 1

select wait_for_executed_gtid_set(gtid_set, 1);
MySQL 5.7.6 版本开始,允许在执行完更新类事务后,把这个事务的 GTID 返回给客户端。具体操作,将参数session_track_gtids 设置为OWN_GTID,调用 API 接口mysql_session_track_get_first 返回结果解析出 GTID 

处理流程:

  • 发起  SQL 操作,在主库成功执行后,返回这个事务的 GTID

  • 发起  SQL 操作时,先在从库执行 select wait_for_executed_gtid_set (gtid_set, 1)

  • 如果返回 0,表示已经从库已经同步了数据,可以在从库执行 查询 操作

  • 否则,在主库执行 查询 操作

缺点:

跟上面的 master_pos_wait 类似,如果 写操作 与 读操作 没有上下文关联,那么 GTID 无法传递 。方案实用性不高。

六、引入缓存中间件

高并发系统,缓存作为性能优化利器,应用广泛。我们可以考虑引入缓存作为缓冲介质

处理过程:

  • 客户端  SQL ,操作主库

  • 同步将缓存中的数据删除

  • 当客户端读数据时,优先从缓存加载

  • 如果 缓存中没有,会强制查询主库预热数据

缺点:

K-V 存储,适用一些简单的查询条件场景。如果复杂的查询,还是要查询从库。

七、数据分片

参考 Redis Cluster 模式, 集群网络拓扑通常是 3主 3从,主节点既负责写,也负责读。

通过水平分片,支持数据的横向扩展。由于每个节点都是独立的服务器,可以提高整体集群的吞吐量。

转换到数据库方面

常见的解决方式,是分库分表,每次读写都是操作主库的一个分表,从库只用来做数据备份。当主库发生故障时,主从切换,保证集群的高可用性。

推荐学习:mysql视频教程

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

WorkBuddy
WorkBuddy

腾讯云推出的AI原生桌面智能体工作台

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
TypeScript类型系统进阶与大型前端项目实践
TypeScript类型系统进阶与大型前端项目实践

本专题围绕 TypeScript 在大型前端项目中的应用展开,深入讲解类型系统设计与工程化开发方法。内容包括泛型与高级类型、类型推断机制、声明文件编写、模块化结构设计以及代码规范管理。通过真实项目案例分析,帮助开发者构建类型安全、结构清晰、易维护的前端工程体系,提高团队协作效率与代码质量。

76

2026.03.13

Python异步编程与Asyncio高并发应用实践
Python异步编程与Asyncio高并发应用实践

本专题围绕 Python 异步编程模型展开,深入讲解 Asyncio 框架的核心原理与应用实践。内容包括事件循环机制、协程任务调度、异步 IO 处理以及并发任务管理策略。通过构建高并发网络请求与异步数据处理案例,帮助开发者掌握 Python 在高并发场景中的高效开发方法,并提升系统资源利用率与整体运行性能。

117

2026.03.12

C# ASP.NET Core微服务架构与API网关实践
C# ASP.NET Core微服务架构与API网关实践

本专题围绕 C# 在现代后端架构中的微服务实践展开,系统讲解基于 ASP.NET Core 构建可扩展服务体系的核心方法。内容涵盖服务拆分策略、RESTful API 设计、服务间通信、API 网关统一入口管理以及服务治理机制。通过真实项目案例,帮助开发者掌握构建高可用微服务系统的关键技术,提高系统的可扩展性与维护效率。

350

2026.03.11

Go高并发任务调度与Goroutine池化实践
Go高并发任务调度与Goroutine池化实践

本专题围绕 Go 语言在高并发任务处理场景中的实践展开,系统讲解 Goroutine 调度模型、Channel 通信机制以及并发控制策略。内容包括任务队列设计、Goroutine 池化管理、资源限制控制以及并发任务的性能优化方法。通过实际案例演示,帮助开发者构建稳定高效的 Go 并发任务处理系统,提高系统在高负载环境下的处理能力与稳定性。

63

2026.03.10

Kotlin Android模块化架构与组件化开发实践
Kotlin Android模块化架构与组件化开发实践

本专题围绕 Kotlin 在 Android 应用开发中的架构实践展开,重点讲解模块化设计与组件化开发的实现思路。内容包括项目模块拆分策略、公共组件封装、依赖管理优化、路由通信机制以及大型项目的工程化管理方法。通过真实项目案例分析,帮助开发者构建结构清晰、易扩展且维护成本低的 Android 应用架构体系,提升团队协作效率与项目迭代速度。

109

2026.03.09

JavaScript浏览器渲染机制与前端性能优化实践
JavaScript浏览器渲染机制与前端性能优化实践

本专题围绕 JavaScript 在浏览器中的执行与渲染机制展开,系统讲解 DOM 构建、CSSOM 解析、重排与重绘原理,以及关键渲染路径优化方法。内容涵盖事件循环机制、异步任务调度、资源加载优化、代码拆分与懒加载等性能优化策略。通过真实前端项目案例,帮助开发者理解浏览器底层工作原理,并掌握提升网页加载速度与交互体验的实用技巧。

108

2026.03.06

Rust内存安全机制与所有权模型深度实践
Rust内存安全机制与所有权模型深度实践

本专题围绕 Rust 语言核心特性展开,深入讲解所有权机制、借用规则、生命周期管理以及智能指针等关键概念。通过系统级开发案例,分析内存安全保障原理与零成本抽象优势,并结合并发场景讲解 Send 与 Sync 特性实现机制。帮助开发者真正理解 Rust 的设计哲学,掌握在高性能与安全性并重场景中的工程实践能力。

243

2026.03.05

PHP高性能API设计与Laravel服务架构实践
PHP高性能API设计与Laravel服务架构实践

本专题围绕 PHP 在现代 Web 后端开发中的高性能实践展开,重点讲解基于 Laravel 框架构建可扩展 API 服务的核心方法。内容涵盖路由与中间件机制、服务容器与依赖注入、接口版本管理、缓存策略设计以及队列异步处理方案。同时结合高并发场景,深入分析性能瓶颈定位与优化思路,帮助开发者构建稳定、高效、易维护的 PHP 后端服务体系。

684

2026.03.04

AI安装教程大全
AI安装教程大全

2026最全AI工具安装教程专题:包含各版本AI绘图、AI视频、智能办公软件的本地化部署手册。全篇零基础友好,附带最新模型下载地址、一键安装脚本及常见报错修复方案。每日更新,收藏这一篇就够了,让AI安装不再报错!

179

2026.03.04

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
MySQL 教程
MySQL 教程

共48课时 | 2.6万人学习

MySQL 初学入门(mosh老师)
MySQL 初学入门(mosh老师)

共3课时 | 0.3万人学习

简单聊聊mysql8与网络通信
简单聊聊mysql8与网络通信

共1课时 | 850人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号