1.声明
当前内容主要用于本人学习和复习之用,当前内容主要为使用Zookeeper实现壁垒的方式控制当前线程什么时候停止什么时候继续
当前内容来源:Barriers伪代码流程
2.查看分析流程
- 客户端调用当前的exists方法,并设置watch为true的方式,设置path为壁垒barrier节点
- 如果当前的exists方法返回的是false,那么这个壁垒消失,客户端继续前进
- 如果当前的exists方法返回的是true,那么当前的客户端等待从barrier获取监控事件,获取壁垒barrier节点
- 当监控事件触发的时候,该客户端重新发出exists调用,再次等待直到移除壁垒节点
下面使用java代码方式实现该壁垒的操作
1.首先开启zookeeper,地址为:192.168.1.105:2181
/**
* @description 当前内容用于实现当前Zookeeper上面的Barriers伪代码
* @author hy
* @date 2020-06-07
*/
public class BarriersTest {
static ZooKeeper zk;
static {
try {
zk=new ZooKeeper("192.168.1.105", 10000, null);
} catch (IOException e) {
System.out.println("初始化失败。。。。");
}
}
//static Watcher watch = ;
static Object mointer =new Object();
public static void main(String[] args) throws KeeperException, InterruptedException {
/*
* 1. Client calls the ZooKeeper API's exists() function on the barrier node,with watch set to true.
* 2. If exists() returns false, the barrier is gone and the client proceeds
* 3. Else, if exists() returns true, the clients wait for a watch event from ZooKeeper for the barrier node.
* 4. When the watch event is triggered, the client reissues the exists( ) call, again waiting until the barrier node is removed.
*/
// 上面是伪代码
// 1. 客户端调用当前的exists方法并设置watch为true的方式,在当前的壁垒barrier节点
// 2. 如果当前的exists方法返回的是false,那么这个壁垒消失,客户端继续前进
// 3.如果当前的exists方法返回的是true,那么当前的客户端等待从barrier获取监控事件,获取壁垒barrier节点
// 4.当监控事件触发的时候,该客户端重新发出exists调用,再次等待直到移除壁垒节点
String barrierNode = "/barrier";
while(true){
synchronized (mointer) {
// 1. 客户端调用当前的exists方法并设置watch为true的方式,在当前的壁垒barrier节点
boolean exists = exists(barrierNode);
if (exists) {
// 3.如果当前的exists方法返回的是true,那么当前的客户端等待从barrier获取监控事件,获取壁垒barrier节点
System.out.println("等待监控事件的触发。。。。");
// 等待获取监控事件
mointer.wait();
} else {
// 2. 如果当前的exists方法返回的是false,那么这个壁垒消失,客户端继续前进
System.out.println("客户端继续前进。。。。");
Thread.sleep(2000L);
}
}
}
}
public static boolean exists(String barrierNode) throws KeeperException, InterruptedException {
Stat stat = zk.exists(barrierNode, new DefaultWatcher(barrierNode));
return stat != null;
}
static class DefaultWatcher implements Watcher {
private String barrierNode;
public DefaultWatcher(String barrierNode) {
this.barrierNode = barrierNode;
}
@Override
public void process(WatchedEvent event) {
try {
synchronized (mointer) {
System.out.println("触发监控事件。。。。。。。。。。");
// 4.当监控事件触发的时候,该客户端重新发出exists调用,再次等待直到移除壁垒节点
if(EventType.NodeDeleted == event.getType()) {
// 壁垒节点被移除的事件
System.out.println("触发节点删除事件。。。。。。。。。。");
mointer.notify();
}
exists(barrierNode);
}
} catch (KeeperException | InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
3.开始测试
1.启动当前的zookeeper
2.启动当前的java客户端
3.为当前的zookeeper创建壁垒节点
create /barrier ""
4.查看当前的控制台
此时发现线程已近停止,并没有持续输出:客户端前进。。。
5.删除壁垒节点
delete /barrier
测试成功
4.总结
1.当前的壁垒实现主要是通过一个标记触发的,这个标记就是壁垒节点是否存在
2.通过为当前壁垒不停的添加监控的事件方式(节点删除)来唤醒当前线程的执行
以上纯属个人见解,如有问题请联本人!