當節點發生變化時,通過watcher機制,可以讓客戶端得到通知,watcher需要實現org.apache.ZooKeeper.Watcher接口。節點的狀態變化主要包含如下
public class ZWatcher implements Watcher { @Override public void process(WatchedEvent event) { // TODO Auto-generated method stub if(event.getType() == EventType.NodeCreated){ System.out.println("創建節點"); } if(event.getType() == EventType.NodeDataChanged){ System.out.println("節點改變"); } if(event.getType() == EventType.NodeChildrenChanged){ System.out.println("子節點節點改變"); } if(event.getType() == EventType.NodeDeleted){ System.out.println("節點刪除"); } } }
需要注意的是watcher是一次性的,也就是處理完一次狀態變化之后需要重新注冊watcher,這點很讓人抓狂。這個特性也使得在處理時間上和重新加載上watcher這段時間發生的節點狀態變化將無法感知。
通常會拋出下面兩種異常:
org.apache.zookeeper.KeeperException$ConnectionLossException: KeeperErrorCode = NodeExists for /root
at org.apache.zookeeper.KeeperException.create(KeeperException.java:119)
at org.apache.zookeeper.KeeperException.create(KeeperException.java:51)
at org.apache.zookeeper.ZooKeeper.create(ZooKeeper.java:783)
客戶機與其中一台服務器socket連接出現異常,連接丟失
org.apache.zookeeper.KeeperException.SessionExpiredException: KeeperErrorCode = Session expired
客戶端的session已經超時sessionTimeout,未進行任何操作。
KeeperException.ConnectionLossException:異常可以通過重試進行處理,客戶端會根據初始化Zookeeper時傳遞的服務列表,自動嘗試下一節點。這段時間內,服務端節點就會丟失
KeeperException.SessionExpiredException:異常不能通過重試進行解決,需要應用重新創建一個新的客戶端(new ZooKeeper()),這是所有的watcher和EPHEMRAL節點都將消失