Zookeeper學習筆記十之 非同步實現主節點選舉
阿新 • • 發佈:2018-12-11
非同步實現主節點選舉
Zookeeper中,所有同步呼叫方法都有對應的非同步呼叫方法,通過非同步呼叫,我們可以在單執行緒中同時進行多個呼叫,接下來實現一個非同步實現主節點選舉的例子
Zookeeper.create方法的非同步呼叫版本
void create(String path, byte data[], List acl, CreateMode createMode, AsyncCallback.StringCallback cb,Object ctx) ,相較於同步呼叫,多了StringCallback ,和Object兩個引數。StringCallback 提供回撥方法的物件,Object使用者指定上下文資訊
程式碼示例
package com.my.service; import java.io.IOException; import java.util.Random; import org.apache.zookeeper.AsyncCallback.DataCallback; import org.apache.zookeeper.AsyncCallback.StringCallback; import org.apache.zookeeper.CreateMode; import org.apache.zookeeper.KeeperException.Code; import org.apache.zookeeper.WatchedEvent; import org.apache.zookeeper.Watcher; import org.apache.zookeeper.Watcher.Event.KeeperState; import org.apache.zookeeper.ZooDefs; import org.apache.zookeeper.ZooKeeper; import org.apache.zookeeper.data.Stat; public class MyZookeeper { private ZooKeeper zooKeeper; private String hostPort; private Random random = new Random(47); private String serverId = Integer.toString(random.nextInt()); boolean isMaster = false; public MyZookeeper(String hostPort) { this.hostPort = hostPort; } // 建立一個zk連線監視點,列印斷開連線日誌資訊 Watcher watcher = new Watcher() { public void process(WatchedEvent event) { // 如果監控到與服務端連線斷開,列印日誌 if (KeeperState.Disconnected.equals(event.getState())) { System.out.println("Zookeeper Disconnected!客戶端與ZooKeeper伺服器連線斷開!"); } } }; // 連線到zk服務端 public void startZk() throws IOException { zooKeeper = new ZooKeeper(hostPort, 15000, watcher); } public void stopZk() throws InterruptedException { zooKeeper.close(); } // 實現一個回撥的介面,並建立例項 StringCallback masterCallback = new StringCallback() { public void processResult(int rc, String path, Object ctx, String name) { switch (Code.get(rc)) {// rc返回呼叫的結構,返回OK或與KeeperException異常對應的編碼值 case CONNECTIONLOSS: checkMasterSync(); return; case OK: //建立成功,成為主節點 isMaster = true; break; default: isMaster = false; } System.out.println("I am" + (isMaster ? "" : "not") + " the master"); } }; // 實現一個檢查資料的回撥介面,並建立例項 DataCallback masterCheckCallBack = new DataCallback() { public void processResult(int rc, String path, Object ctx, byte[] data, Stat stat) { switch (Code.get(rc)) { case CONNECTIONLOSS: checkMasterSync(); return; case NONODE: //主節點不存在,進行非同步主節點建立 runForMasterSync(); return; } } }; public void checkMasterSync() { zooKeeper.getData("/master", false, masterCheckCallBack, null); } public void runForMasterSync() { zooKeeper.create("/master", serverId.getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL, masterCallback, null); } public static void main(String[] args) throws IOException, InterruptedException { MyZookeeper myZookeeper = new MyZookeeper("127.0.0.1:2181"); myZookeeper.startZk(); myZookeeper.runForMasterSync(); //執行緒休眠一段時間,觀看非同步建立效果 Thread.sleep(5000); if (myZookeeper.isMaster) { System.out.println("我是主節點"); Thread.sleep(60000); } else { System.out.println("其他節點已經成為了主節點"); } } }