mysql读写分离有四种实现方式:1.应用层实现,通过代码判断sql类型路由;2.中间件代理(如mycat、shardingsphere-proxy),对应用透明;3.mysql connector/j原生支持,轻量级主从连接配置;4.shardingsphere-jdbc客户端嵌入方案,支持精细路由与负载均衡。

Java 应用本身不直接配置 MySQL 的读写分离与负载均衡,而是通过**中间件代理**或**客户端驱动支持**来实现。核心思路是:让 Java 程序连接一个“逻辑地址”,由该地址背后的组件(如 ProxySQL、ShardingSphere-JDBC、MyCat 或 MySQL Connector/J 自带的 replica 机制)自动识别 SQL 类型、选择主库或从库,并在多个从库间做负载分发。
用 MySQL Connector/J 原生支持(轻量级,无需额外服务)
MySQL 官方 JDBC 驱动(8.0+)内置了简单的读写分离能力,适合中小规模、对强一致性要求不极端的场景。
- 连接 URL 示例(含主从地址和策略):
jdbc:mysql://address=(type=master)(host=192.168.1.101)(port=3306),(type=slave)(host=192.168.1.102)(port=3306),(type=slave)(host=192.168.1.103)(port=3306)/mydb?loadBalanceStrategy=random&allowPublicKeyRetrieval=true&useSSL=false&serverTimezone=UTC -
关键参数说明:
–address=():定义多个节点,标注type=master或type=slave
–loadBalanceStrategy=random:支持random、bestResponseTime、leastConnections
–readFromMasterWhenNoSlaves=true(可选):所有从库不可用时自动切回主库读取 - 注意事项:
– 主从复制必须已配置好,且延迟可控;
– 不支持复杂路由规则(如SELECT ... FOR UPDATE强制走主库),需业务层规避;
– 无连接池管理、无查询缓存、无运行时权重调整等高级功能。
集成 ShardingSphere-JDBC(推荐,纯 Java 客户端方案)
这是 Apache 顶级项目,以 Jar 包形式嵌入 Java 应用,零运维依赖,支持精细控制,是当前主流选择。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- Maven 引入:
org.apache.shardingsphere shardingsphere-jdbc-core-spring-boot-starter 5.4.0 - application.yml 配置示例:
spring:
shardingsphere:
mode: Standalone
datasource:
ds-master:
driver-class-name: com.mysql.cj.jdbc.Driver
jdbc-url: jdbc:mysql://192.168.1.101:3306/mydb
username: root
password: pwd
ds-slave-0:
driver-class-name: com.mysql.cj.jdbc.Driver
jdbc-url: jdbc:mysql://192.168.1.102:3306/mydb
username: root
password: pwd
ds-slave-1:
driver-class-name: com.mysql.cj.jdbc.Driver
jdbc-url: jdbc:mysql://192.168.1.103:3306/mydb
username: root
password: pwd
rules:
- !READWRITE_SPLITTING
dataSources:
readwrite_ds:
writeDataSourceName: ds-master
readDataSourceNames: [ds-slave-0, ds-slave-1]
loadBalancerName: random
loadBalancers:
random:
type: RANDOM - 优势:
– 支持 SQL 解析,自动识别SELECT走从库,INSERT/UPDATE/DELETE走主库;
– 可配置强制走主库(如HintManager),解决主从延迟导致的一致性问题;
– 内置熔断、权重、响应时间感知等负载策略;
– 与 Spring Boot 深度集成,无需改代码,只换数据源 Bean。
对接 ProxySQL(独立中间件,适合多语言统一治理)
当团队有 PHP、Go、Python 等其他语言服务共用同一套 MySQL 架构时,部署 ProxySQL 是更合理的中心化方案。Java 应用只需像连普通 MySQL 一样连接 ProxySQL 的 6033 端口。
- ProxySQL 需预先配置:
– 添加主库(hostgroup 10)、从库(hostgroup 20);
– 创建监控用户、后端用户;
– 插入路由规则:
INSERT INTO mysql_query_rules (rule_id, active, match_pattern, destination_hostgroup, apply) VALUES (1, 1, '^SELECT.*FOR UPDATE', 10, 1);
INSERT INTO mysql_query_rules (rule_id, active, match_pattern, destination_hostgroup, apply) VALUES (2, 1, '^SELECT', 20, 1); - Java 连接串(指向 ProxySQL):
jdbc:mysql://192.168.1.100:6033/mydb?user=proxy_user&password=proxy_pass - 好处:
– 所有语言复用同一套路由逻辑;
– 支持查询缓存、连接池复用、实时监控、故障自动摘除;
– Java 应用完全无感,不引入额外依赖,升级/灰度更安全。
避坑提醒
无论采用哪种方式,以下几点直接影响效果:
- 主从复制必须稳定:建议启用 半同步复制(
rpl_semi_sync_master_enabled=ON),避免从库延迟过大导致脏读; - 从库设为
read_only=ON,防止误操作写入; - 业务中慎用
SELECT ... FOR UPDATE、SELECT ... LOCK IN SHARE MODE,这类语句必须走主库,否则会报错或数据不一致; - 测试阶段务必验证:执行写操作后立即读,确认是否能查到最新结果(即检验主从延迟容忍度);
- 不要在事务中混用主从——一个事务内所有 SQL 必须路由到同一节点,否则会失败。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










