想搞清楚ZooKeepe?这篇入门你必须了解,springcloud教程视频

            if (Event.KeeperState.SyncConnected == state) {
                Event.EventType type = watchedEvent.getType();
                if (Event.EventType.None == type) {
                    System.out.println("zk客户端已连接...");
                }
            }
        }
    });
    zooKeeper.create("/java", "Hello World".getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);
    System.out.println("新增ZNode成功");
    zooKeeper.close();
}

创建一个持久性ZNode,路径是/java,值为"Hello World":

![](https://upload-images.jianshu.io/upload_images/24195226-f9f90a5e25c7c34c.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

# 七、API概述

## 7.1 创建

public String create(final String path, byte data[], List acl, CreateMode createMode)


参数解释:

*   path ZNode路径
*   data ZNode存储的数据
*   acl ACL权限控制
*   createMode ZNode类型

ACL权限控制,有三个是ZooKeeper定义的常用权限,在ZooDefs.Ids类中:

/**

  • This is a completely open ACL.
  • 完全开放的ACL,任何连接的客户端都可以操作该属性znode
    */
    public final ArrayList OPEN_ACL_UNSAFE = new ArrayList(Collections.singletonList(new ACL(Perms.ALL, ANYONE_ID_UNSAFE)));

/**

  • This ACL gives the creators authentication id’s all permissions.
  • 只有创建者才有ACL权限
    */
    public final ArrayList CREATOR_ALL_ACL = new ArrayList(Collections.singletonList(new ACL(Perms.ALL, AUTH_IDS)));

/**

  • This ACL gives the world the ability to read.
  • 只能读取ACL
    */
    public final ArrayList READ_ACL_UNSAFE = new ArrayList(Collections.singletonList(new ACL(Perms.READ, ANYONE_ID_UNSAFE)));

createMode就是前面讲过的四种ZNode类型:

public enum CreateMode {
/**
* 持久性ZNode
/
PERSISTENT (0, false, false),
/
*
* 持久性自动增加顺序号ZNode
/
PERSISTENT_SEQUENTIAL (2, false, true),
/
*
* 临时性ZNode
/
EPHEMERAL (1, true, false),
/
*
* 临时性自动增加顺序号ZNode
*/
EPHEMERAL_SEQUENTIAL (3, true, true);
}


## 7.2 查询

//同步获取节点数据
public byte[] getData(String path, boolean watch, Stat stat){

}

//异步获取节点数据
public void getData(final String path, Watcher watcher, DataCallback cb, Object ctx){

}


同步getData()方法中的stat参数是用于接收返回的节点描述信息:

public byte[] getData(final String path, Watcher watcher, Stat stat){
//省略…
GetDataResponse response = new GetDataResponse();
//发送请求到ZooKeeper服务器,获取到response
ReplyHeader r = cnxn.submitRequest(h, request, response, wcb);
if (stat != null) {
//把response的Stat赋值到传入的stat中
DataTree.copyStat(response.getStat(), stat);
}
}


使用同步getData()获取数据:

//数据的描述信息,包括版本号,ACL权限,子节点信息等等
Stat stat = new Stat();
//返回结果是byte[]数据,getData()方法底层会把描述信息复制到stat对象中
byte[] bytes = zooKeeper.getData("/java", false, stat);
//打印结果
System.out.println("ZNode的数据data:" + new String(bytes));//Hello World
System.out.println("获取到dataVersion版本号:" + stat.getVersion());//默认数据版本号是0

## 7.3 更新

public Stat setData(final String path, byte data[], int version){

}


值得注意的是第三个参数version,**使用CAS机制,这是为了防止多个客户端同时更新节点数据,所以需要在更新时传入版本号,每次更新都会使版本号+1**,如果服务端接收到版本号,对比发现不一致的话,则会抛出异常。

所以,在更新前需要先查询获取到版本号,否则你不知道当前版本号是多少,就没法更新:

//获取节点描述信息
Stat stat = new Stat();
zooKeeper.getData("/java", false, stat);
System.out.println("更新ZNode数据...");
//更新操作,传入路径,更新值,版本号三个参数,返回结果是新的描述信息
Stat setData = zooKeeper.setData("/java", "fly!!!".getBytes(), stat.getVersion());
System.out.println("更新后的版本号为:" + setData.getVersion());//更新后的版本号为:1

更新后,版本号增加了:

![](https://upload-images.jianshu.io/upload_images/24195226-99b96debd2050544.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)


如果传入的版本参数是"-1",就是告诉zookeeper服务器,客户端需要基于数据的最新版本进行更新操作。但是-1并不是一个合法的版本号,而是一个标识符。

## 7.4 删除

public void delete(final String path, int version){

}


*   path 删除节点的路径
*   version 版本号

这里也需要传入版本号,调用getData()方法即可获取到版本号,很简单:

Stat stat = new Stat();
zooKeeper.getData("/java", false, stat);
//删除ZNode
zooKeeper.delete("/java", stat.getVersion());


## 7.5 watcher机制

在上面第三点提到,ZooKeeper是可以使用通知监听机制,当ZNode发生变化会收到通知消息,进行处理。基于watcher机制,ZooKeeper能玩出很多花样。怎么使用?

ZooKeeper的通知监听机制,总的来说可以分为三个过程:

①客户端注册 Watcher ②服务器处理 Watcher ③客户端回调 Watcher客户端。

注册 watcher 有 4 种方法,new ZooKeeper()、getData()、exists()、getChildren()。下面演示一下使用exists()方法注册watcher:

首先**需要实现Watcher接口**,新建一个监听器:

public class MyWatcher implements Watcher {
@Override
public void process(WatchedEvent event) {
//获取事件类型
Event.EventType eventType = event.getType();
//通知状态
Event.KeeperState eventState = event.getState();
//节点路径
String eventPath = event.getPath();
System.out.println(“监听到的事件类型:” + eventType.name());
System.out.println(“监听到的通知状态:” + eventState.name());
System.out.println(“监听到的ZNode路径:” + eventPath);
}
}


然后调用exists()方法,注册监听器:

zooKeeper.exists("/java", new MyWatcher());
//对ZNode进行更新数据的操作,触发监听器
zooKeeper.setData("/java", “fly”.getBytes(), -1);


然后在控制台就可以看到打印的信息:

![](https://upload-images.jianshu.io/upload_images/24195226-6d4f24d7fe63fffe.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)


这里我们可以看到**Event.EventType对象就是事件类型**,我们可以对事件类型进行判断,再配合**Event.KeeperState通知状态**,做相关的业务处理,事件类型有哪些?

打开EventType、KeeperState的源码查看:

//事件类型是一个枚举
public enum EventType {
None (-1),//无
NodeCreated (1),//Watcher监听的数据节点被创建
NodeDeleted (2),//Watcher监听的数据节点被删除
NodeDataChanged (3),//Watcher监听的数据节点内容发生变更
NodeChildrenChanged (4);//Watcher监听的数据节点的子节点列表发生变更
}

//通知状态也是一个枚举
public enum KeeperState {
Unknown (-1),//属性过期
Disconnected (0),//客户端与服务端断开连接
NoSyncConnected (1),//属性过期
SyncConnected (3),//客户端与服务端正常连接
AuthFailed (4),//身份认证失败
ConnectedReadOnly (5),//返回这个状态给客户端,客户端只能处理读请求
SaslAuthenticated(6),//服务器采用SASL做校验时
Expired (-112);//会话session失效
}


### 7.5.1 watcher的特性

*   一次性。一旦watcher被触发,ZK都会从相应的存储中移除。

最后

在面试前我整理归纳了一些面试学习资料,文中结合我的朋友同学面试美团滴滴这类大厂的资料及案例
感兴趣的朋友可以点击Java学习免费获取。

MyBatis答案解析
由于篇幅限制,文档的详解资料太全面,细节内容太多,所以只把部分知识点截图出来粗略的介绍,每个小节点里面都有更细化的内容!

大家看完有什么不懂的可以在下方留言讨论也可以关注。

觉得文章对你有帮助的话记得关注我点个赞支持一下!

的朋友可以点击Java学习免费获取。**
[外链图片转存中…(img-Gpya0PlO-1628624732493)]

[外链图片转存中…(img-7cXBSwku-1628624732496)]
由于篇幅限制,文档的详解资料太全面,细节内容太多,所以只把部分知识点截图出来粗略的介绍,每个小节点里面都有更细化的内容!

大家看完有什么不懂的可以在下方留言讨论也可以关注。

觉得文章对你有帮助的话记得关注我点个赞支持一下!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值