
============================================================= MySQL读写分离知识整理 Craft6.cn 颜超敏 ============================================================= ------------------------------------------------------------- 1 一些定义 ------------------------------------------------------------- 1.1 原理 1.1.1 实际应用中,数据库都是读多写少 1.1.2 Master负责数据库更新和实时数据查询,Slave库负责非实时数据查询 1.1.3 一台服务器作为主机,一台或多台服务器作为从机。主机会把数据库的变化记录到日志。 一旦这些变化被记录到日志,就会立刻(或者以设定的时间间隔)被送到从机。 1.1.4 通常将查询从主库抽取出来,采用多个从库,使用负载均衡,减轻每个从库的查询压力 1.2 复制 1.2.1 异步复制 1.2.1.1 异步复制意味着在把数据从一台机器拷贝到另一台机器时有一个延时 1.2.1.2 当应用系统的事务提交已经确认时数据并不能在同一时刻拷贝/应用到从机 1.2.1.3 通常这个延时是由网络带宽、资源可用性和系统负载决定的 1.2.2 同步复制 1.2.2.1 同步复制可以定义为数据在同一时刻被提交到一台或多台机器 1.2.2.2 通常这是通过众所周知的“两阶段提交”做到的 ------------------------------------------------------------- 2 分离原则 ------------------------------------------------------------- 2.1 内容分离 2.1.1 根据内容分离,针对某个表或者某个库的查询到哪个服务器上。 2.2 按负荷状态选择 2.2.1 根据后端mysql服务器的状态,当第一台服务器到达某个标准状态 时候再请求到第二台服务器上。这种原则容易造成第一台服务器长时间的高负载运行。 2.3 按session分离 2.3.1 根据session分离,根据session和后端服务器的映射表来分离。 ------------------------------------------------------------- 3 可选方案 ------------------------------------------------------------- 3.1 通过程序实现 3.1.1 原理 3.1.1.1 定义两个数据库连接 3.1.1.2 更新时调用 MasterDataSource 3.1.1.3 查询时调用 SlaveDataSource 3.1.2 Spring 3.1.2.1 动态数据源切换 3.1.2.2 在程序运行时,把数据源动态织入程序,从而选取主库还是从库 3.1.2.3 annotation、Spring AOP、反射等 3.2 通过mysq-proxy 3.2.1 使用lua脚本实现,如果lua开发不够理想,风险会比较大 3.2.2 性能不高 3.3 自己开发接口实现 3.4 阿里的Amoeba实现 ------------------------------------------------------------- 4 通过程序实现 ------------------------------------------------------------- 4.1 基于JDBC 4.1.1 使用 ReplicationDriver 建立Connection 4.1.2 Connection conn = driver.connect( "jdbc:mysql://master,slave1,slave2,slave3/test", props); 4.1.3 通过 readOnly 参数 true/false 控制是连接主数据库还是从数据库 4.1.4 参考链接 4.1.4.1 http://www.iteye.com/topic/205926 4.2 基于Spring开发 4.2.1 AbstractRoutingDataSource 4.2.1.1 继承AbstractDataSource ,实现javax.sql.DataSource接口 4.2.1.2 determineTargetDataSource()方法 4.2.1.3 从注入的数据源Map集合中,根据lookupKey获得DataSource实例 4.2.2 DynamicDataSource 4.2.2.1 自行实现的子类,继承AbstractRoutingDataSource 4.2.2.2 实现系统的determineCurrentLookupKey逻辑 4.2.2.3 即什么情况下返回那个数据源的key 4.2.3 DynamicDataSourceHolder 4.2.3.1 通过ThreadLocal保存当前的数据源key 4.2.4 DataSourceAspect 4.2.4.1 AOP部分的实现 4.2.4.2 往Holder中设置数据源key 4.2.4.3 在dao的方法中,通过注解设置该方法调用哪个数据源 4.2.5 参考链接 4.2.5.1 http://www.cnblogs.com/surge/p/3582248.html 4.2.5.2 http://985.so/d2Ex ------------------------------------------------------------- 5 MySQL Proxy ------------------------------------------------------------- 5.1 http://www.jb51.net/article/29818.htm 5.2 http://blog.csdn.net/e421083458/article/details/19697701 ------------------------------------------------------------- 6 自己实现 ------------------------------------------------------------- 6.1 如人人网的ICE框架 6.1.1 http://blog.csdn.net/cuibinghua84/article/details/6834383 ------------------------------------------------------------- 7 Amoeba ------------------------------------------------------------- 7.1 介绍 7.1.1 分布式数据库 proxy 开发。座落与Client、DB Server(s)之间。 对客户端透明。具有负载均衡、高可用性、sql过滤、 读写分离、可路由相关的query到目标数据库、可并发请求多台数据库合并结果。 7.2 安装和配置 amoeba-mysql 7.3 参考链接 7.3.1 http://985.so/d2Bc ------------------------------------------------------------- 8 其它参考文章 ------------------------------------------------------------- 8.1 http://985.so/d2AX