为了保证可用性,传统的关系型数据库(mysql)通常采用一主多备的方式,当主宕机后,切换到备机。

有多种方式可以做到主备自动失效检测切换,比如传统的HA软件heartbeat,keepalived等等,采取虚拟IP的方式对客户端透明;

这里主备自动切换方案没有采取VIP的方式,而是用zookeeper对数据库集群进行管理,可以做到主备失效检测切换,主库的选举,

比如考虑到mysql对多核利用率不高而一个节点部署多个mysql实例,如果采用VIP的方式是不可行的。

基本做法是,每个mysql实例上部署一个agent节点,agent负责对该mysql实例定时进行ping操作,agent在zookeeper上注册临时节点,

如果agent或者该agent代理的mysql宕掉,注册在zookeeper上的节点就会发生变化,利用zookeeper watch功能实现mysq实例失效后的主库的选举操作,

读节点也通过watch master节点的功能实现指向新的master。

如上图所示,zookeeper上的master节点存储当前主节点名称;

servers下面保存在线的节点,命名规则一般为ip:port_序列号;

nodeid为当前的序列号,每当节点获取一个序列号时,该节点值自就增,以便于分配给下一个节点。

过程如下:

a、初始化阶段,创建servers,master,nodeid节点

b、每个client创建servers子节点,zoo_create("/servers/xxx",EPHEMERAL)

c、zoo_get_child(/servers,NULL)

d、若当前client的序列号id是当前最小的节点,则当前节点是master,设置master节点退出

e、否则,zoo_exsists(lastid before id,watcher)//当前节点watch比当前节点id次小的那个节点的状态

如果id不存在,那么退出

否则等待watch触发,重新选举master

相关伪代码参考示例如下:

try {

ProposoWatcher wc = new ProposoWatcher();

final ZooKeeper zk = new ZooKeeper("10.1.1.24:2181", 60000, wc);

wc.setZk(zk);

if (zk.exists("/master", false) == null) {

zk.create("/master", null, Ids.OPEN_ACL_UNSAFE,

CreateMode.PERSISTENT);

}

zk.create("/servers/" + nodeName, new byte[0], Ids.OPEN_ACL_UNSAFE,

CreateMode.EPHEMERAL);

List list = zk.getChildren("/servers", false);

String[] nodes = list.toArray(new String[list.size()]);

Arrays.sort(nodes);

if (nodeName.equals(nodes[0])) {//初次

System.out.println("this is master" + nodes[0]);

zk.setData("/master", nodeName.getBytes(), -1);

} else {

// 监控比自己次小的Node

String lower = "";

for (int i = 0; i < nodes.length; i++) {

if (nodeName.equals(nodes[i])) {

lower = nodes[i - 1];

break;

}

}

zk.exists("/servers/" + lower, true);

}

} catch (Exception e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

//watcher

public static class ProposoWatcher implements Watcher {

private ZooKeeper zk;

public ZooKeeper getZk() {

return zk;

}

public void setZk(ZooKeeper zk) {

this.zk = zk;

}

@Override

public void process(WatchedEvent event) {

// TODO Auto-generated method stub

switch (event.getType()) {

case None: {

// connectionEvent(event);

break;

}

case NodeDeleted: {

// servers.remove(event.getPath());

System.out.println("node  removed**" + event.getPath());

String delName = event.getPath().substring(

event.getPath().lastIndexOf("/"));

// final ZooKeeper zk1 = zk;

List children = new ArrayList();

try {

children = zk.getChildren("/servers", false);

} catch (KeeperException e) {

// TODO Auto-generated catch block

e.printStackTrace();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

String[] nodes = children.toArray(new String[children.size()]);

Arrays.sort(nodes);

for (int i = 0; i < nodes.length; i++) {

if (nodes[i].compareTo(delName) > 0) {

// TODO:curr Node become master

System.out.println("this is master" + nodes[i]);

try {

zk.setData("/master", nodes[i].getBytes(), -1);

} catch (KeeperException e) {

// TODO Auto-generated catch block

e.printStackTrace();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

break;

}

}

break;

}

}

}

}

mysql zookeeper 切换_zookeeper在mysql主库选举切换中的应用相关推荐

  1. Linux服务器安装JavaWeb环境(二) Redis,MySql,Zookeeper,Keepalive

    /*****************[安装RedisServer]****************/ 第一步:下载redis安装包 http://download.redis.io/releases/ ...

  2. MySQL 集群(三):MySQL + Mycat 实现读写分离,主备切换集群

    MySQL 集群(三):MySQL + Mycat 实现读写分离,主从切换集群 下载 Mycat Mycat 主要文件 端口 Mycat 命令 配置文件 server.xml schema.xml 配 ...

  3. mysql keepalived低版本_Mysql+keepalived主主切换

    Mysql+keepalived主主切换 一,环境介绍 网络结构: VIP :192.168.1.30 MYSQL A:192.168.1.21 MYSQL B:192.168.1.22 二.mysq ...

  4. mycat mysql 主从切换_Mycat读写分离与主从切换

    环境说明 本文的环境信息: 192.168.1.248: slave节点 192.168.1.250: master节点 数据库服务准备工作 主从配置完成后,Slave_IO_Running和Slav ...

  5. drbd实现mysql地热备_heartheartbeat+drbd+mysql主库热备

    1 环境 主机名 网卡 磁盘 master eth0 桥接模式 eth0(192.168.1.10) 自定义模式(VMnet2)(192.168.2.10)VIP 192.168.1.200/210 ...

  6. mysql 5.7 主从切换_mysql5.7 主从复制的正常切换【转】

    目前环境如下: master server IP:172.17.61.131 slave server IP:172.17.61.132 mysql version: mysql-5.7.21-lin ...

  7. mybatis mysql merge_Spring Boot + Mybatis 整合Mysql ,SQLServer数据源以及整合druid,动态调整数据源切换。...

    pom.xml依赖 org.springframework.boot spring-boot-starter-web org.mybatis.spring.boot mybatis-spring-bo ...

  8. typechoSQLIte转MySQL_Typecho SQLite与MySQL的数据库切换及解决MySQL连接打开缓慢问题

    (本科水平,写得不好请不吝指点 ) Ⅰ Abstract Typecho开源轻量级博客系统拥有WordPress主题插件二次开发等一系列优点,但相比于WordPress笨重复杂的操作,Typecho赢 ...

  9. Linux企业运维 6.6 -- Redis部署及主从切换、Redis+Mysql读写分离

    目录 Redis简介 redis的编译.安装 1.server1的redis配置 2.server2的redis安装 3.server3配置redis 三.redis主从复制 四.Sentine主从自 ...

最新文章

  1. 小牛生产小牛的问题解决集粹
  2. 简书 SSH 登录流程分析
  3. 转载 1-EasyNetQ介绍(黄亮翻译) https://www.cnblogs.com/HuangLiang/p/7105659.html
  4. 18道经典MySQL面试题,祝您升职加薪
  5. 指标搭建篇:如何快速定位数据异常?——ROI异常实战案例
  6. listview嵌套gridview
  7. 初中计算机课教什么时候,初中计算机教学课程教学方法探讨
  8. mysql5.0无法访问_MYSQL版本升级到后5.0后无法连接的问题
  9. Raid3.0数据丢失怎么办
  10. docker安装和启动zookeeper,数据导入及导出
  11. Inception模块 GooLeNet网络
  12. 【Android机器学习实战】3、定制可点击View、目标检测、以图搜图实战
  13. iOS之UITableViewController的使用
  14. 微信录制视频转圈效果如何实现?
  15. 创新实训(9)——SpringBoot整合solr
  16. 软件工程知识点总结汇总
  17. 整理的一篇iOS面试题大全
  18. 转:解救西西弗斯- 模型驱动架构(MDA,Model Driven Architecture)浅述
  19. 为何人工智能用Python这门编程语言?
  20. Traceroute命令原理及使用(路由跟踪)

热门文章

  1. Ajax简单异步上传图片并回显
  2. Google I/O 2014 - Keynote for Android
  3. BP神经网络的Java实现(转载)
  4. hdu_5701_中位数计数
  5. Android Contextual Menus之二:contextual action mode
  6. 测试类图Head First 设计模式 (九) 迭代器与组合模式(Iterator Composite pattern) C++实现...
  7. PostgreSQL学习手册(系统表)
  8. C#里调用带输出参数的存储过程
  9. VISUAL STUDIO 2019 快捷键
  10. 挖掘机实现“无人驾驶”!协作机器人“魔法之手”取代人工操作