MySQL分库分表与集群技术详解
interview 项目地址: https://gitcode.com/gh_mirrors/intervi/interview
分库分表概述
随着业务规模不断扩大,单机MySQL数据库往往会遇到性能瓶颈。此时,分库分表成为解决数据库扩展性问题的有效手段。分库分表主要分为垂直拆分和水平拆分两种方式。
垂直拆分方案
垂直分表
垂直分表是将一个大表按照字段进行拆分,把不常用或占用空间大的字段分离到扩展表中。这种拆分方式:
- 减少单表宽度,避免查询时加载过多无用数据
- 解决text等大字段导致的off-page问题
- 提高高频查询字段的缓存命中率
典型场景:用户表将基本信息与详细资料分离
垂直分库
垂直分库是按照业务维度将不同业务的数据拆分到不同的数据库实例中:
- 每个业务使用独立的数据库实例
- 不同业务的数据物理隔离
- 避免单机资源成为瓶颈
优势:
- 降低单库连接数压力
- 提高业务隔离性
- 便于按业务扩展
水平拆分方案
水平拆分主要解决单表数据量过大的问题,通过某种规则将数据分散到多个表或库中。
分片策略
-
离散映射:如取模分片(uid%n)
- 优点:数据分布均匀
- 缺点:扩容需数据迁移
-
连续映射:如按时间范围分片
- 优点:避免数据迁移
- 缺点:存在热点问题
三阶段扩容方案
阶段一:初始状态
- 单库双表:DB0包含t0、t1
- 分片规则:id%2
阶段二:首次扩容
- 新增DB1库
- 将DB0.t0迁移到DB1.t1
- 新增t0_1、t1_1表存放新数据
- 分片规则:
- 1千万以下:id%2到t0/t1
- 1-2千万:id%2到t0_1/t1_1
阶段三:二次扩容
- 新增DB2、DB3库
- 将DB0.t0_1迁移到DB2
- 将DB1.t1_1迁移到DB3
- 新增t0_2等4个表
- 分片规则调整为id%4
数据迁移方案
-
停机迁移
- 流程简单安全
- 需要业务停服
- 适合小型系统
-
双写迁移
- 三个阶段:
- 历史数据导入+双写(老库为准)
- 双写(新库为准)+查询切新库
- 稳定后下线老库
- 无需停服
- 实现复杂
- 三个阶段:
分库分表后的问题解决
Join操作问题
- 全局表:将基础数据在所有库冗余存储
- 字段冗余:空间换时间,需考虑一致性
- 系统层组装:通过服务调用拼装数据
分布式ID生成
- 数据库自增ID:简单但性能受限
- UUID:无序影响索引性能
- Snowflake算法:
- 64位ID结构
- 包含时间戳、机器ID、序列号
- 需解决时钟回拨问题
改进版Snowflake:
- 秒级时间戳(32位)
- 21位序列号
- 环形列表缓存序列
MySQL主从复制
复制线程
- Log Dump Thread:主节点发送binlog
- I/O Thread:从节点接收binlog
- SQL Thread:从节点重放relay log
同步模式
- 异步模式:性能最好,数据一致性最弱
- 半同步模式:平衡性能与一致性
- 全同步模式:强一致,性能最差
主从延迟优化
- 优化网络质量
- 降低主库负载
- 从库专用于备份
- 多线程复制(按schema并行)
总结
分库分表是MySQL应对大数据量场景的必备技术,需要根据业务特点选择合适的拆分策略。同时,主从复制提供了数据冗余和读写分离能力。在实际应用中,还需要考虑分布式事务、全局ID等问题,构建完整的分布式数据库解决方案。
interview 项目地址: https://gitcode.com/gh_mirrors/intervi/interview
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考