Zookeeper

用于分布式项目统一的文件管理(配置文件)

用于服务的注册中心

1.Zokeeper操作

默认端口2182

基本节点操作

1.启动zkServer和引入zookeeper包
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-zookeeper-config</artifactId>
</dependency>
2.开启连接
zooKeeper = new ZooKeeper("172.16.1.136:2181",50000,null);            
3.创建节点
String result = zooKeeper.create("/javaNode/mynode", "java".getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);
System.err.println(result);
4.修改节点
Stat stat = zooKeeper.setData("/javaNode/mynode", "mysql".getBytes(), -1);
if(stat != null){
    System.err.println(stat.getVersion());
}
5.修改节点
/*修改节点数据,版本默认-1,每次操作+1*/
Stat stat = zooKeeper.setData("/javaNode/mynode", "mysql".getBytes(), -1);
if(stat != null){
	System.err.println(stat.getVersion());
}
6.删除节点
zooKeeper.delete("/javaNode/mynode",-1);
7.获取节点的描述信息
Stat exists = zooKeeper.exists("/javaNode/mynode", false);
if(exists != null){
    System.err.println(exists.getAversion());
    System.err.println(exists.getCtime());
    System.err.println(exists.getDataLength());
    System.err.println(exists.getNumChildren());
}
8.获取所有的子节点
List<String> children = zooKeeper.getChildren("/", null);
for (String child : children) {
	System.out.println(child);
}

监控操作Watch

watch用于监控zookeeper节点的变化,比如当子节点删除时,用于通知其他的程序进行相应的操作

1.重写Watch方法
class Mywatch implements Watcher{
@Override
	public void process(WatchedEvent watchedEvent) {
        System.out.println("发生变化的路径:"+watchedEvent.getPath());
        System.out.println("发生变化的状态:"+watchedEvent.getState());
        System.out.println("发生变化的类型:"+watchedEvent.getType());
        System.out.println("发生变化的warp:"+watchedEvent.getWrapper());
	}
}

2.调用该watch类(exist方法是可以监听创建,而getData无法监听创建)

exist方法是可以监听创建,而getData无法监听创建

getChildren()方法是可以监听创建和删除,但是不能监听子节点的修改

 @Test
 public void watchTest() throws IOException, KeeperException, InterruptedException {
     ZooKeeper zooKeeper = new ZooKeeper("172.16.1.136:2181",50000,null);  
     /*exist方法是可以监听创建,而getData无法监听创建*/
     //byte[] data = zooKeeper.getData("/javaNode", new Mywatch(), null);
	/*getChildren()方法是可以监听创建和删除,但是不能监听子节点的修改*/
     //List<String> children = zooKeeper.getChildren("/javaNode", new Mywatch());
     
     Stat exists = zooKeeper.exists("/javaNode", new Mywatch());
     System.out.println("是否存在结果:"+exists);
     while (true) {

	}
}

3.当节点无变化时(此时已存在一个/javaNode的节点)Zookeeper

  • 这时候,如果对该节点进行删除操作
delete /javaNode

Zookeeper

结果:

Zookeeper

  • 创建节点

Zookeeper

create /javaNode java1

结果:Zookeeper

控制台没有发生变化,因为这个监控器watch是一次触发,监听了一次结束就没了

2.应用场景

  • 当分布式开发项目之中存在一个集群,zookeeper将他们的共有的配置文件集中管理,当其中配置文件发生改动时,可以通过监听,及时更新到各个所连接节点上的服务器上,确保配置文件的一致性

  • 当其中一台集群中的服务器故障之后,通过监听可以反映到服务器集群中(临时节点断掉,父节点可以接受到节点断掉的变化),从而及时剔除该故障服务器(从配置文件之中删除故障服务器的配置),以免造成故障服务器还接受请求的情况

Zookeeper

- 保持独占:通过写入数据成功,就添加一个特有的节点,这个节点就是锁,其他程序只能等待

- 控制时序:创建顺序节点,编号最小的那个节点可以先拿到锁

3.Zookeeper服务注册和发现

Zookeeper

  • 服务提供者开发结束就在zookeeper添加一个节点
  • 服务消费者要使用服务的时候,先访问zookeeper查看特定服务节点,对发现的几个服务发送请求
  • 当服务提供者新增或者删除服务,都会在zookeeper上进行注册,但是服务消费者并不关系服务的变化,能处理自己的请求就可以了,这样一来,达到一个解耦的效果.

zookeeper可以在长连接的时候可以代替一个反向代理的作用,通过特定的算法,将固定ip地址的连接,通过注册中心,发送给对应的服务

Zookeeper