• SpringBoot3集成Zookeeper


    标签:Zookeeper3.8 ,Curator5.5;

    一、简介

    ZooKeeper是一个集中的服务,用于维护配置信息、命名、提供分布式同步、提供组服务。分布式应用程序以某种形式使用所有这些类型的服务。

    二、环境搭建

    1、修改配置文件

    # 1、拷贝一份样本配置文件
    cp zookeeper-3.8.3/conf/zoo_sample.cfg zookeeper-3.8.3/conf/zoo.cfg
    
    # 2、修改数据文件地址,注意这里用本地路径
    dataDir=/local-path/zookeeper-3.8.3/data
    
    # 3、添加一个配置,处理启动日志的提示:ZooKeeper audit is disabled.
    audit.enable=true
    

    2、服务启动

    # 1、启动服务端
    zookeeper-3.8.3/bin/zkServer.sh start
    
    # 2、停止服务端
    zookeeper-3.8.3/bin/zkServer.sh stop
    
    # 3、启动客户端
    zookeeper-3.8.3/bin/zkCli.sh
    

    3、客户端测几个增删查的命令

    [zk: localhost:2181(CONNECTED) 0] create /cicada smile1
    Created /cicada
    [zk: localhost:2181(CONNECTED) 1] get /cicada
    smile1
    [zk: localhost:2181(CONNECTED) 2] ls /
    [cicada, zookeeper]
    [zk: localhost:2181(CONNECTED) 3] delete /cicada
    

    三、工程搭建

    1、工程结构

    2、依赖管理

    Curator是一组Java库,它让ZooKeeper的使用变得更加容易,这里的依赖实际是查询匹配版本的时候走了个捷径,也可以参考integration-redis包,熟悉下Spring的封装策略。

    
    <dependency>
        <groupId>org.apache.zookeepergroupId>
        <artifactId>zookeeperartifactId>
        <version>${zookeeper.version}version>
    dependency>
    
    <dependency>
        <groupId>org.springframework.integrationgroupId>
        <artifactId>spring-integration-zookeeperartifactId>
        <version>${spring-integration.version}version>
    dependency>
    

    3、配置文件

    配置脚本

    zookeeper:
      #服务器地址
      connectString: 127.0.0.1:2181
      #会话超时时间
      sessionTimeoutMs: 3000
      #连接超时时间
      connectionTimeoutMs: 60000
      #最大重试次数
      maxRetries: 3
      #初始休眠时间
      baseSleepTimeMs: 1000
    

    配置类

    @Configuration
    public class ZookeeperConfig {
    
        @Value("${zookeeper.connectString}")
        private String connectString;
        
        @Value("${zookeeper.baseSleepTimeMs}")
        private int baseSleepTimeMs;
    
        @Value("${zookeeper.maxRetries}")
        private int maxRetries ;
    
        @Value("${zookeeper.connectionTimeoutMs}")
        int connectionTimeoutMs ;
    
        @Value("${zookeeper.sessionTimeoutMs}")
        int sessionTimeoutMs ;
    
        private static CuratorFramework client = null ;
        /**
         * 初始化
         */
        @PostConstruct
        public void init (){
            // 重试策略
            RetryPolicy policy = new ExponentialBackoffRetry(baseSleepTimeMs, maxRetries);
            // 创建Curator
            client = CuratorFrameworkFactory.builder()
                    .connectString(connectString)
                    .connectionTimeoutMs(connectionTimeoutMs)
                    .sessionTimeoutMs(sessionTimeoutMs)
                    .retryPolicy(policy).build();
            //开启连接
            client.start();
        }
    
        @Bean
        public CuratorFramework getClient (){
            return client ;
        }
    }
    

    四、ZooKeeper用法

    测试几个API方法,节点创建和添加数据,以及判断和查询数据,还有就是基于ZooKeeper提供的读写锁能力。

    public class ConfigTest {
    
        @Autowired
        private CuratorFramework client ;
    
        @Test
        public void testCreate () throws Exception {
            // 创建一个持久化节点,断开连接时不会自动删除
            client.create().creatingParentsIfNeeded().withMode(CreateMode.PERSISTENT).forPath("/path1");
        }
    
        @Test
        public void testExists () throws Exception {
            // 判断节点是否存在,path2不存在所以stat2是null
            Stat stat1 = client.checkExists().forPath("/path1");
            System.out.println(stat1);
            Stat stat2 = client.checkExists().forPath("/path2");
            System.out.println(stat2);
        }
    
        @Test
        public void testSetData () throws Exception {
            // 设置节点数据
            client.setData().forPath("/path1", "data1".getBytes(StandardCharsets.UTF_8));
        }
    
        @Test
        public void testCreateAndSet () throws Exception {
            // 创建一个持久化节点并设置节点数据
            client.create().creatingParentsIfNeeded().withMode(CreateMode.PERSISTENT)
                    .forPath("/path3","data3".getBytes(StandardCharsets.UTF_8));
        }
    
        @Test
        public void testGetData () throws Exception {
            // 查询节点数据
            byte[] data = client.getData().forPath("/path3");
            System.out.println(new String(data,StandardCharsets.UTF_8));
        }
    
        @Test
        public void testDelete () throws Exception {
            // 删除节点
            client.delete().guaranteed().deletingChildrenIfNeeded().forPath("/path3");
        }
    
        @Test
        public void testReadLock () throws Exception {
            // 读写锁-读
            InterProcessReadWriteLock lock = new InterProcessReadWriteLock(client,"/lock-read");
            lock.readLock().acquire();
            System.out.println("获取-ReadLock");
            lock.readLock().release();
        }
    
        @Test
        public void testWriteLock () throws Exception {
            // 读写锁-写
            InterProcessReadWriteLock lock = new InterProcessReadWriteLock(client,"/lock-write");
            lock.writeLock().acquire();
            System.out.println("获取-WriteLock");
            lock.writeLock().release();
        }
    }
    

    五、参考源码

    文档仓库:
    https://gitee.com/cicadasmile/butte-java-note
    
    源码仓库:
    https://gitee.com/cicadasmile/butte-spring-parent
    
  • 相关阅读:
    零基础Linux_17(进程间通信)VSCode环境安装+进程间通信介绍+pipe管道mkfifo
    lamba stream处理集合
    如何判断一个js对象是否存在循环引用
    测试报告模板一
    子域名访问计数(哈希表、字符串、索引)
    转换纳米材料NaY(Gd/Lu/Nd):Yb,Er,Nd@NaYF6:Yb,Nd包裹/修饰油酸Oleic acid/氨基NH2/羧基COOH
    mybatis逆向工程(pom文件和generatorConfig.xml)的配置
    Vue3中使用i18n,this.$t报错
    双十二买什么牌子电容笔?值得买的平价电容笔推荐
    [蓝牙 Mesh & Zephyr]-[004]- 基础 Model
  • 原文地址:https://www.cnblogs.com/cicada-smile/p/17982849