zookeeper之基础学习篇

1.ZooKeeper简介

ZooKeeper是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现,是Hadoop和Hbase的重要组件。它是一个为分布式应用提供一致性服务的软件,提供的功能包括:配置维护、域名服务、分布式同步、组服务等。 —— [ 百度百科 ]

  ZooKeeper的目标就是封装好复杂易出错的关键服务,将简单易用的接口和性能高效、功能稳定的系统提供给用户。
  ZooKeeper使用Java语言编写,但是支持Java和C两种编程语言。

2.ZooKeeper数据结构

zookeeper数据结构

2.1.znode的概念

  每个子目录如/Baidu都被称作一个znode(节点)。这个znode是被它所在的路径唯一标识。
  znode可以有子节点目录,并且每个znode可以存储数据。
  znode是有版本的,每个znode中存储的数据可以有多个版本,也就是一个访问路径中可以存储多份数据。
  znode可以被监控,包括这个目录节点中存储数据的修改、子目录的修改等,一旦变化可以通知设置监控的客户端。

2.2.znode的分类

持久节点(PERSISTENT):是指在节点创建后就一直存在,直到有删除操作来主动清除这个节点,不会因为创建该节点的客户端会话失效而消失。
持久顺序节点(PERSISTENT_SEQUENTIAL):这类节点的基本特性和上面的节点是一致的。额外的特性是,在zookeeper中每个父节点会为他的第一级子结点维护一份时序,会记录每个子节点创建的先后顺序。在创建子节点的过程中会自动给节点名加上一个数字后缀作为新的节点名。这个数字后缀的范围是整形的最大值。
临时节点(EPHEMERAL):如果客户端会话失效(不是连接断开),那么这个节点就会自动被擦除掉。临时节点下面不能创建子节点。
临时顺序节点(EPHEMERAL_SEQUENTIAL):以此类推。

3.ZooKeeper简单使用

我将zookeeper安装到我的虚拟机上,移步 [下载地址] 。

3.1.安装

1.下载解压之后将conf包下的zoo_sample.cfg文件拷贝一本重命名为zoo.cfg

[root@localhost conf]# cp zoo_sample.cfg zoo.cfg

2.修改zoo.cfg

# 其他的可以使用默认主要就是这两项,放在哪里自己高兴就好
dataDir=/usr/local/zookeeper-3.4.11/data/data
dataLogDir=/usr/local/zookeeper-3.4.11/data/log-data

3.2.启动与停止

当我们看到QuorumPeerMain就说明启动成功了。

[root@localhost bin]# ./zkServer.sh start
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper-3.4.11/bin/../conf/zoo.cfg
Starting zookeeper ... STARTED
[root@localhost bin]# jps
1593 QuorumPeerMain
1610 Jps
[root@localhost bin]# ./zkServer.sh stop
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper-3.4.11/bin/../conf/zoo.cfg
Stopping zookeeper ... ./bin/zkServer.sh: line 182: kill: (1814) - No such process
STOPPED

3.3.linux命令的简单使用

启动客户端:

[root@localhost zookeeper-3.4.11]# ./bin/zkCli.sh 

查询命令:ls 路径

[zk: localhost:2181(CONNECTED) 0] ls /

查询值命令:get 路径

[zk: localhost:2181(CONNECTED) 1] get /node1
aaa
...

创建命令:create [-s] [-e] path data
加上-e是临时节点,加-s是顺序节点。

[zk: localhost:2181(CONNECTED) 3] create /node2 bbb
Created /node2

最后客户端的退出肯定是老生常谈的quit了。

4.ZooKeeper的java使用

直接甩一个测试类。

public class TestZkClient {
    private ZkClient zkClient;
    @Before
    public void testBefore(){
        zkClient = new ZkClient("IP:2181",20000,2000, new SerializableSerializer());
    }
    // 创建节点并绑定数据
    @Test
    public void testTest1(){
        String name = zkClient.create("/java1","hello word", CreateMode.PERSISTENT);
        // 绑定对象数据
        //zkClient.createEphemeral("",null);
        System.out.println(name);
    }
    // 获取节点上的数据
    @Test
    public void testTest2(){
        Object data = zkClient.readData("/java1");
        System.out.println(data);
    }
    // 修改节点上的数据
    @Test
    public void testTest3(){
        zkClient.updateDataSerialized("/java1",(oldData) -> oldData+"!!!");
    }
    // 删除节点
    @Test
    public void testTest4(){
        // 如果该节点下面有子节点,那么需要用到下面的递归删除
        boolean b = zkClient.delete("/java1");
        System.out.println(b);
        //zkClient.deleteRecursive("/java1");
    }
    @Test
    public void testTest5(){
        zkClient.subscribeDataChanges("/java1",new IZkDataListener(){
            @Override
            public void handleDataChange(String s, Object o) throws Exception {
                System.out.println("节点"+s+"变更为"+o);
            }
            @Override
            public void handleDataDeleted(String s) throws Exception {
                System.out.println("节点"+s+"被删除");
            }
        });
    }
    @After
    public void testAfter(){
        zkClient.close();
    }
}

猜你喜欢

转载自blog.csdn.net/roubaoyin/article/details/79978066