zk抢主
package com.autonavi.tinfo.t1.traffic.pub.openlr.util;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import org.apache.zookeeper.Watcher.Event.KeeperState;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.github.zkclient.IZkChildListener;
import com.github.zkclient.IZkStateListener;
import com.github.zkclient.ZkClient;
public class StatusMonitor {
private Lock lock = new ReentrantLock();// 锁对象
private boolean usingHA = true;
private volatile boolean isLeader = false;
private static final Logger logger = LoggerFactory.getLogger(StatusMonitor.class);
// 超时时间
private int zkSessionTimeOut=5000;
private int zkConnectionTimeOut=5000;
//private int SESSION_TIMEOUT = 5000;
//private int CONNECTION_TIMEOUT = 5000;
// zookeeper server列表
private String zkServerList = "10.17.132.71:2181";
private String zkServerDir = "fast-update";
private String subNode = "openlr";
// 当前client创建的子节点
private String curPath;
private ZkClient zkClient;
ScheduledExecutorService intervalMonitorExecutor = Executors.newSingleThreadScheduledExecutor();
/**
* 连接zookeeper
*/
public void init() {
logger.info("StatusMonitor.init zkSessionTimeOut:{},zkConnectionTimeOut:{}",zkSessionTimeOut,zkConnectionTimeOut);
try {
connect();
} catch (Exception e) {
this.isLeader = false;
logger.error(e.getMessage(), e);
try {
connect();
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
logger.error("error occurs during sync data from zk");
System.exit(0);
} finally {
;
}
}
intervalMonitorExecutor.scheduleAtFixedRate(new Runnable() {
@Override
public void run() {
lock.lock();
try {
if (zkClient == null) {
isLeader = false;
return;
}
if (zkClient != null && zkClient.getZooKeeper() == null) {
isLeader = false;
return;
}
if (zkClient != null && (!zkClient.getZooKeeper().getState().isAlive()
|| !zkClient.getZooKeeper().getState().isConnected())) {
isLeader = false;
return;
}
} finally {
lock.unlock();
}
}
}, 0, 2, TimeUnit.SECONDS);
}
public void connect() throws Exception {
if (!usingHA) {
return;
}
if (this.zkClient != null) {
this.zkClient.close();
}
this.zkClient = new ZkClient(zkServerList, zkSessionTimeOut, zkConnectionTimeOut);
if (!zkClient.exists("/" + zkServerDir)) {
zkClient.createPersistent("/" + zkServerDir, null);
}
if (curPath == null) {
curPath = zkClient.createEphemeralSequential("/" + zkServerDir + "/" + subNode, "monitor".getBytes());
}
try {
startWatchingTopicStatus();
} catch (Exception e) {
// TODO Auto-generated catch block
logger.error(e.getMessage(), e);
logger.error("error occurs during sync data from zk");
System.exit(0);
}
Thread.sleep(2000);// */
handleMonitorNodeChange();
}
public void startWatchingTopicStatus() {
ZkTopicStatusListener topicEventListener = new ZkTopicStatusListener();
ZkConnectedStatusListener connectedStatusListener = new ZkConnectedStatusListener();
try {
zkClient.subscribeChildChanges("/" + zkServerDir, topicEventListener);
zkClient.subscribeStateChanges(connectedStatusListener);
} catch (Exception e) {
logger.error(e.getMessage(), e);
try {
Thread.sleep(1000);
} catch (InterruptedException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
startWatchingTopicStatus();
}
}
public void stop() {
if (zkClient == null) {
logger.warn("shutdown topic event watcher");
return;
}
// stopWatchingTopicEvents();
zkClient.close();
zkClient = null;
}
private void beLeader() {
logger.info("this node gains lock {} and becomes leader ", curPath);
System.out.println("this node gains lock " + curPath + " and becomes leader");
this.isLeader = true;
}
public void setUsingHA(boolean isUsingHA) {
this.usingHA = isUsingHA;
}
public void setZkServerDir(String zkServerDir) {
this.zkServerDir = zkServerDir;
}
public boolean isUsingHA() {
return usingHA;
}
public boolean isLeader() {
return isLeader;
}
public void setZkServerList(String zkServerList) {
this.zkServerList = zkServerList;
}
/*public int getSESSION_TIMEOUT() {
return SESSION_TIMEOUT;
}
public void setSESSION_TIMEOUT(int sESSION_TIMEOUT) {
SESSION_TIMEOUT = sESSION_TIMEOUT;
}
public int getCONNECTION_TIMEOUT() {
return CONNECTION_TIMEOUT;
}
public void setCONNECTION_TIMEOUT(int cONNECTION_TIMEOUT) {
CONNECTION_TIMEOUT = cONNECTION_TIMEOUT;
}*/
public int getZkSessionTimeOut() {
return zkSessionTimeOut;
}
public void setZkSessionTimeOut(int zkSessionTimeOut) {
this.zkSessionTimeOut = zkSessionTimeOut;
}
public int getZkConnectionTimeOut() {
return zkConnectionTimeOut;
}
public void setZkConnectionTimeOut(int zkConnectionTimeOut) {
this.zkConnectionTimeOut = zkConnectionTimeOut;
}
public void handleMonitorNodeChange() throws Exception {
this.lock.lock();
try {
if (zkClient == null)
return;
if (!zkClient.exists("/" + zkServerDir)) {
zkClient.createPersistent("/" + zkServerDir, null);
}
// 确认curPath是否真的是列表中的最小节点
List<String> childs = zkClient.getChildren("/" + zkServerDir);
if (childs == null || childs.size() == 0) {
// 创建子节点
curPath = zkClient.createEphemeralSequential("/" + zkServerDir + "/" + subNode, "monitor".getBytes());
childs = zkClient.getChildren("/" + zkServerDir);
}
Collections.sort(childs);
String thisNode = curPath.substring(("/" + zkServerDir + "/").length());
int index = childs.indexOf(thisNode);
if (index < 0) {
curPath = zkClient.createEphemeralSequential("/" + zkServerDir + "/" + subNode, "monitor".getBytes());
childs = zkClient.getChildren("/" + zkServerDir);
Collections.sort(childs);
thisNode = curPath.substring(("/" + zkServerDir + "/").length());
index = childs.indexOf(thisNode);
}
if (index == 0) {
// 确实是最小节点
beLeader();
} else {
this.isLeader = false;
}
} finally {
this.lock.unlock();
}
}
class ZkTopicStatusListener implements IZkChildListener {
@Override
public void handleChildChange(String parentPath, List<String> currentChilds) throws Exception {
handleMonitorNodeChange();
}
}
class ZkConnectedStatusListener implements IZkStateListener {
@Override
public void handleStateChanged(KeeperState state) throws Exception {
// TODO Auto-generated method stub
if (state.equals(state.SyncConnected) || state.equals(state.ConnectedReadOnly)) {
System.out.println("zookeeper start to be connected");
handleMonitorNodeChange();
}
}
@Override
public void handleNewSession() throws Exception {
// TODO Auto-generated method stub
}
}
public static void main(String[] args) throws Exception {
StatusMonitor statusMonitor = new StatusMonitor();
statusMonitor.setZkServerList("10.61.97.23:2181");
statusMonitor.setUsingHA(true);
statusMonitor.init();
Thread.sleep(100000000);
}
}
zk抢主的更多相关文章
- Zookeeper笔记之使用zk实现集群选主
一.需求 在主从结构的集群中,我们假设硬件机器是很脆弱的,随时可能会宕机,当master挂掉之后需要从slave中选出一个节点作为新的master,使用zookeeper可以很简单的实现集群选主功能. ...
- zookeeper分布式服务中选主的应用
通常zookeeper在分布式服务中作为注册中心,实际上它还可以办到很多事.比如分布式队列.分布式锁 由于公司服务中有很多定时任务,而这些定时任务由于一些历史原因暂时不能改造成框架调用 于是想到用zo ...
- zookeeper典型应用场景之一:master选举
对于zookeeper这种东西,仅仅知道怎么安装是远远不够的,至少要对其几个典型的应用场景进行了解,才能比较全面的知道zk究竟能干啥,怎么玩儿,以后的日子里才能知道这货如何能为我所用.于是,有了如下的 ...
- Zookeeper客户端Curator的使用,简单高效
Curator是Netflix公司开源的一个Zookeeper客户端,与Zookeeper提供的原生客户端相比,Curator的抽象层次更高,简化了Zookeeper客户端的开发量. 1.引入依赖: ...
- zookeeper选举机制
在上一篇文章中我们大致浏览了zookeeper的启动过程,并且提到在Zookeeper的启动过程中leader选举是非常重要而且最复杂的一个环节.那么什么是leader选举呢?zookeeper为什么 ...
- ZooKeeper 典型应用场景-Master选举
master选举 1.使用场景及结构 现在很多时候我们的服务需要7*24小时工作,假如一台机器挂了,我们希望能有其它机器顶替它继续工作.此类问题现在多采用master-salve模式,也就是常说的主从 ...
- zookeeper master 选举
原文地址: http://www.cnblogs.com/nevermorewang/p/5611807.html 选主原理介绍:zookeeper的节点有两种类型,持久节点跟临时节点.临时节点有个特 ...
- zookeeper 笔记--curator分布式锁
使用ZK实现分布式独占锁, 原理就是利用ZK同级节点的唯一性. Curator框架下的一些分布式锁工具InterProcessMutex:分布式可重入排它锁 InterProcessSemaphore ...
- 大数据学习(22)—— ZooKeeper能做些什么
官网上已经给出了zk的几种典型应用场景,原话是这么说的: It exposes a simple set of primitives that distributed applications can ...
随机推荐
- WCF开发指南之构建服务
一. 引言 Windows通讯基础(简称为WCF)是一种SDK,用于让你使用典型的CLR编程结构(例如用于发布和消费服务的类和接口等)来构建Windows面向服务的应用程序.WCF的编程模型是声明性的 ...
- 3、通过挂在系统光盘搭建本地yum仓库的方法
1. mkdir xxx #新建文件夹 (新建一个挂载需要的文件夹) .配置本地yum源(挂载光盘) .进入 yum.repos.d .ls (查看当前文件夹全部的文件) 并 mv 修改 除Med ...
- Python操作文件文档
需要帮老师将44G的图书分类一下,人工当然累死了.所以用Python大法处理一下. 思路是读取文件目录下的书名,然后去百度百科查分类,如果还没有就去豆瓣,当当查.哪一个先找到其余的就不用找了.如果没有 ...
- MySQL日期 字符串 时间戳互转
平时比较常用的时间.字符串.时间戳之间的互相转换,虽然常用但是几乎每次使用时候都喜欢去搜索一下用法:本文将作为一个笔记,整理一下三者之间的 转换(即:date转字符串.date转时间戳.字符串转dat ...
- 上下margin重叠传递问题
我发现强迫症真的是我一个大病...每次都非得把所有情况都实验出来不可...BUT!!!!!!!!!悲催的是,这么多情况我根本记不住...还是要在写代码的时候不断出错再排错~受不了自己了!不过还是把这部 ...
- 《JavaScript模式》第5章 对象创建模式
@by Ruth92(转载请注明出处) 第5章:对象创建模式 JavaScript 是一种简洁明了的语言,并没有其他语言中经常使用的一些特殊语法特征,如 命名空间.模块.包.私有属性 以及 静态成员 ...
- json_decode时含有中文是解码问题(json_decode返回为null)
function myDecode($str){ $str = substr(str_replace('\"','"',json_encode($str)),1,-1); retu ...
- 9.9,新iPhone要来了,是欢呼,还是墙角画圈,一会儿见分晓
- jquery dataTables.min.js API
demo: http://datatables.net/release-datatables/examples/api/select_single_row.html 选择一行http://datata ...
- UVa 10129单词(欧拉回路)
https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem& ...