Zookeeper:JavaAPI watcher机制
1.watcher架构
watcher由三个部分组成:
zookeeper服务端、zookeeper客户端、客户端的ZKWatchManager对象。
接口设计:
Watcher接口中含有一个内部接口Event,其中含有两个枚举KeeperStat(通知状态)和EventType(事件类型)
public enum KeeperState { /** Unused, this state is never generated by the server */ @Deprecated Unknown (-1), /** The client is in the disconnected state - it is not connected * to any server in the ensemble. */ Disconnected (0), /** Unused, this state is never generated by the server */ @Deprecated NoSyncConnected (1), /** The client is in the connected state - it is connected * to a server in the ensemble (one of the servers specified * in the host connection parameter during ZooKeeper client * creation). */ SyncConnected (3), /** * Auth failed state */ AuthFailed (4), /** * The client is connected to a read-only server, that is the * server which is not currently connected to the majority. * The only operations allowed after receiving this state is * read operations. * This state is generated for read-only clients only since * read/write clients aren't allowed to connect to r/o servers. */ ConnectedReadOnly (5), /** * SaslAuthenticated: used to notify clients that they are SASL-authenticated, * so that they can perform Zookeeper actions with their SASL-authorized permissions. */ SaslAuthenticated(6), /** The serving cluster has expired this session. The ZooKeeper * client connection (the session) is no longer valid. You must * create a new client connection (instantiate a new ZooKeeper * instance) if you with to access the ensemble. */ Expired (-112); private final int intValue; // Integer representation of value // for sending over wire KeeperState(int intValue) { this.intValue = intValue; } public int getIntValue() { return intValue; } public static KeeperState fromInt(int intValue) { switch(intValue) { case -1: return KeeperState.Unknown; case 0: return KeeperState.Disconnected; case 1: return KeeperState.NoSyncConnected; case 3: return KeeperState.SyncConnected; case 4: return KeeperState.AuthFailed; case 5: return KeeperState.ConnectedReadOnly; case 6: return KeeperState.SaslAuthenticated; case -112: return KeeperState.Expired; default: throw new RuntimeException("Invalid integer value for conversion to KeeperState"); } } }
public enum EventType { None (-1), NodeCreated (1), NodeDeleted (2), NodeDataChanged (3), NodeChildrenChanged (4); private final int intValue; // Integer representation of value // for sending over wire EventType(int intValue) { this.intValue = intValue; } public int getIntValue() { return intValue; } public static EventType fromInt(int intValue) { switch(intValue) { case -1: return EventType.None; case 1: return EventType.NodeCreated; case 2: return EventType.NodeDeleted; case 3: return EventType.NodeDataChanged; case 4: return EventType.NodeChildrenChanged; default: throw new RuntimeException("Invalid integer value for conversion to EventType"); } } }
以node节点为例,说明调用的注册方法和可监听时间间的关系:
注册方式 | Created | ChildrenChanged | Changed | Deleted |
zk.exists("/node",watcher) | 可监控 | 可监控 | 可监控 | |
zk.getData("/node",watcher) | 可监控 | 可监控 | ||
zk.getChildren("/node",watcher) | 可监控 | 可监控 |
2.注册Watcher
KeeperState 通知状态
public class ZKWatcher implements Watcher{ static CountDownLatch latch = new CountDownLatch(1); static ZooKeeper zooKeeper; public static void main(String[] args) throws Exception{ Watcher watcher; zooKeeper = new ZooKeeper("192.168.10.132:2181", 5000, new ZKWatcher()); latch.await(); } public void process(WatchedEvent event) { if(event.getType() == Event.EventType.None){ if(event.getState() == Event.KeeperState.SyncConnected){ System.out.println("连接成功"); latch.countDown(); }else if(event.getState() == Event.KeeperState.Disconnected){ System.out.println("断开连接"); }else if(event.getState() == Event.KeeperState.Expired){ System.out.println("会话超时"); }else if(event.getState() == Event.KeeperState.AuthFailed){ System.out.println("认证失败"); } } } }
3.检查节点是否存在
//使用链接对象的监视器 exists(String path,boolean b) //自定义监视器 exists(String path,Watacher watcher) //NodeCreated:节点创建 //NodeDeleted:节点删除 //NodeDataChanged:节点内容发生变化
4.查看节点
//使用连接对象的监视器 getData(String path,boolean b,Stat stat) //自定义监视器 getData(String path,Watcher w,Stat stat) //NodeDeleted:节点删除 //NodeDataChanged:节点内容变化
5.查看子节点
//使用连接对象的监视器 getChildren(String path,boolean b) //自定义监视器 getChildren(String path,Watcher w) //NodeDeleted:节点删除 //NodeChildrenChanged:子节点内容变化