• Centos或Windows中部署Zookeeper集群及其简单用法


    一、简介

      ZooKeeper是一个分布式的,开放源码的分布式应用程序协调服务,是Google的Chubby一个开源的实现,是Hadoop和Hbase的重要组件。它是一个为分布式应用提供一致性服务的软件,提供的功能包括:配置维护、域名服务、分布式同步、组服务等。
    ZooKeeper的目标就是封装好复杂易出错的关键服务,将简单易用的接口和性能高效、功能稳定的系统提供给用户。

    二、环境

      Windows或者Centos7,本例中使用Centos7测试,Windows上的用和Linux是相似的,只是启动解本执行对应.bat而不是.sh即可。

    三、部署

      1、下载最新版(3.4.13):https://archive.apache.org/dist/zookeeper/  下载https://archive.apache.org/dist/zookeeper/zookeeper-3.4.13/zookeeper-3.4.13.tar.gz解压开即可。

      2、解压开后,进入conf目录:

        (a)如果是要配置单节点,则然后复制并重命名zoo_sample.cfg文件为zoo.cfg,然后修改zoo.cfg如下:

    # The number of milliseconds of each tick
    tickTime=2000
    # The number of ticks that the initial 
    # synchronization phase can take
    initLimit=10
    # The number of ticks that can pass between 
    # sending a request and getting an acknowledgement
    syncLimit=5
    # the directory where the snapshot is stored.
    # do not use /tmp for storage, /tmp here is just 
    # example sakes.
    dataDir=D:\Applicaton\DevTools\Zookeeper\zookeeper-3.4.13\data
    dataLogDir=D:\Applicaton\DevTools\Zookeeper\zookeeper-3.4.13\log
    # the port at which the clients will connect
    clientPort=2181
    # the maximum number of client connections.
    # increase this if you need to handle more clients
    #maxClientCnxns=60
    #
    # Be sure to read the maintenance section of the 
    # administrator guide before turning on autopurge.
    #
    # http://zookeeper.apache.org/doc/current/zookeeperAdmin.html#sc_maintenance
    #
    # The number of snapshots to retain in dataDir
    #autopurge.snapRetainCount=3
    # Purge task interval in hours
    # Set to "0" to disable auto purge feature
    #autopurge.purgeInterval=1

        配置说明:

    tickTime:zookeeper中使用的基本时间单位, 毫秒值。 
    initLimit:这个配置项是用来配置 Zookeeper 接受客户端(这里所说的客户端不是用户连接 Zookeeper 服务器的客户端,而是 Zookeeper 服务器集群中连接到 Leader 的 Follower 服务器)初始化连接时最长能忍受多少个 tickTime 时间间隔数。这里设置为5表名最长容忍时间为 5 * 2000 = 10 秒。 
    syncLimit:这个配置标识 Leader 与 Follower 之间发送消息,请求和应答时间长度,最长不能超过多少个 tickTime 的时间长度,总的时间长度就是 2 * 2000 = 4 秒。 
    dataDir 和 dataLogDir 看配置就知道干吗的了,不用解释,Windows上和Linux上都可以,配置相应目录即可,使用\来作的转义。 
    clientPort:监听client连接的端口号,这里说的client就是连接到Zookeeper的代码程序。 
    server.{myid}={ip}:{leader服务器交换信息的端口}:{当leader服务器挂了后, 选举leader的端口} 
    maxClientCnxns:对于一个客户端的连接数限制,默认是60,这在大部分时候是足够了。但是在我们实际使用中发现,在测试环境经常超过这个数,经过调查发现有的团队将几十个应用全部部署到一台机器上,以方便测试,于是这个数字就超过了。

        (b)如果是要配置多节点,则复制并重命名zoo_sample.cfg为zoo.server1.cfg、zoo.server2.cfg、zoo.server3.cfg三个文件,并追加server.<myid>=<serverIP>:<Leader交换信息端口>:<当Leader挂了后选举Leader的端口>。

    server.{myid}={ip}:{leader服务器交换信息的端口}:{当leader服务器挂了后, 选举leader的端口} 

      其中zoo.server1.cfg内容如下:

    # sending a request and getting an acknowledgement
    syncLimit=5
    # the directory where the snapshot is stored.
    # do not use /tmp for storage, /tmp here is just 
    # example sakes.
    dataDir=/tmp/zookeeper/server1
    # the port at which the clients will connect
    clientPort=2181
    # the maximum number of client connections.
    # increase this if you need to handle more clients
    #maxClientCnxns=60
    #
    # Be sure to read the maintenance section of the 
    # administrator guide before turning on autopurge.
    #
    # http://zookeeper.apache.org/doc/current/zookeeperAdmin.html#sc_maintenance
    #
    # The number of snapshots to retain in dataDir
    #autopurge.snapRetainCount=3
    # Purge task interval in hours
    # Set to "0" to disable auto purge feature
    #autopurge.purgeInterval=1i
    server.1=127.0.0.1:2888:3888
    server.2=127.0.0.1:2889:3889
    server.3=127.0.0.1:2890:3890

      其中zoo.server2.cfg内容如下:

    # The number of milliseconds of each tick
    tickTime=2000
    # The number of ticks that the initial 
    # synchronization phase can take
    initLimit=10
    # The number of ticks that can pass between 
    # sending a request and getting an acknowledgement
    syncLimit=5
    # the directory where the snapshot is stored.
    # do not use /tmp for storage, /tmp here is just 
    # example sakes.
    dataDir=/tmp/zookeeper/server2
    # the port at which the clients will connect
    clientPort=2182
    
    # the maximum number of client connections.
    # increase this if you need to handle more clients
    #maxClientCnxns=60
    #
    # Be sure to read the maintenance section of the 
    # administrator guide before turning on autopurge.
    #
    # http://zookeeper.apache.org/doc/current/zookeeperAdmin.html#sc_maintenance
    #
    # The number of snapshots to retain in dataDir
    #autopurge.snapRetainCount=3
    # Purge task interval in hours
    # Set to "0" to disable auto purge feature
    #autopurge.purgeInterval=1i
    server.1=127.0.0.1:2888:3888
    server.2=127.0.0.1:2889:3889
    server.3=127.0.0.1:2890:3890

      其中zoo.server3.cfg内容如下:

    # The number of milliseconds of each tick
    tickTime=2000
    # The number of ticks that the initial 
    # synchronization phase can take
    initLimit=10
    # The number of ticks that can pass between 
    # sending a request and getting an acknowledgement
    syncLimit=5
    # the directory where the snapshot is stored.
    # do not use /tmp for storage, /tmp here is just 
    # example sakes.
    dataDir=/tmp/zookeeper/server3
    # the port at which the clients will connect
    clientPort=2183
    # the maximum number of client connections.
    # increase this if you need to handle more clients
    #maxClientCnxns=60
    #
    # Be sure to read the maintenance section of the 
    # administrator guide before turning on autopurge.
    #
    # http://zookeeper.apache.org/doc/current/zookeeperAdmin.html#sc_maintenance
    #
    # The number of snapshots to retain in dataDir
    #autopurge.snapRetainCount=3
    # Purge task interval in hours
    # Set to "0" to disable auto purge feature
    #autopurge.purgeInterval=1i
    server.1=127.0.0.1:2888:3888
    server.2=127.0.0.1:2889:3889
    server.3=127.0.0.1:2890:3890

      3、创建数据目录:

      如果前面的配置是使用多节点集群模式时,请在相应的数据dataDir参数的目录下面创建一个名为myid的文件,内容就写各个服务器的myid标记,例如:前面的多节点配置中,在/tmp/zookeeper/server1、/tmp/zookeeper/server2、/tmp/zookeeper/server3目录下分别创建一个名为myid的文件,内容分别是:1、2、3。

      可用下列角本快速创建实现:

    echo 1>/tmp/zookeeper/server1/myid
    echo 2>/tmp/zookeeper/server2/myid
    echo 3>/tmp/zookeeper/server3/myid

      如果不配置此步,则会出现下列错误:Caused by: java.lang.IllegalArgumentException: /tmp/zookeeper/server3/myid file is missing

      3、启动程序

      (a)如果是单节点程序,则进入zookeeper解压目录下执行:./bin/zkServer.sh start即可,系统默认会查找./conf/zoo.cfg作为配置文件。在Windows上则直接执行/bin/zkServer.bat即可。

      (b)如果是多节点程序,则进入zookeeper解压目录下分别执行:

    ./bin/zkServer.sh start ./conf/zoo.server1.cfg
    ./bin/zkServer.sh start ./conf/zoo.server2.cfg
    ./bin/zkServer.sh start ./conf/zoo.server3.cfg

       (c)使用ss -tanl或者netstat -lpen命令检查服务是否已启动。

     三、用法

      Zookeeper提供了Java操作的API,用法网上一找一大堆,本文就讲讲C#使用Zookeeper.net库操作的方法。

      (1)新建Netframework控制台项目,并Nuget引入下列包:https://www.nuget.org/packages/ZooKeeper.Net/

      (2)日志配置:

        (a)在项目中新建log4net.config文件,并设置输出方式为:【如果较新则复制】 内容如下:

    <?xml version="1.0" encoding="UTF-8"?>
    
    <configuration status="ON">
      <log4net>
        <!--<appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">
          <layout type="log4net.Layout.PatternLayout" value="%date [%thread] %-5level %logger - %message%newline" />
        </appender>-->
        <appender name="RollingLogFileAppender" type="log4net.Appender.RollingFileAppender">
          <file value="logs/" />
          <appendToFile value="true" />
          <rollingStyle value="Composite" />
          <staticLogFileName value="false" />
          <datePattern value="yyyyMMdd'.log'" />
          <maxSizeRollBackups value="10" />
          <maximumFileSize value="1MB" />
          <layout type="log4net.Layout.PatternLayout">
            <conversionPattern value="%date [%thread] %-5level %logger [%property{NDC}] - %message%newline" />
          </layout>
        </appender>
        <root level="WARN">
          <!--<appender-ref ref="ConsoleAppender" />-->
          <appender-ref ref="RollingLogFileAppender" />
        </root>
      </log4net>
    </configuration>

      (3)新建类:MyWatcher,内容如下:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using ZooKeeperNet;
    
    namespace ZookeeperDemo
    {
        class MyWatcher : ZooKeeperNet.IWatcher
        {
            public void Process(WatchedEvent @event)
            {
                var old = Console.ForegroundColor;
                Console.ForegroundColor = ConsoleColor.Yellow;
                Console.WriteLine(">>>>> Path:" + @event.Path + "   State:" + @event.State + "   Type:" + @event.Type);
                Console.ForegroundColor = old;
            }
        }
    }

      (4)在Program类中,注意连接集群时,用","分隔主机与Port。这样写:

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading;
    using System.Threading.Tasks;
    using ZooKeeperNet;
    
    namespace ZookeeperDemo
    {
        class Program
        {
            static void Main(string[] args)
            {
                //配置日志
                log4net.Config.XmlConfigurator.Configure(new System.IO.FileInfo("log4net.config"));
                //测试Zookeper
                using (ZooKeeperNet.ZooKeeper zk = new ZooKeeperNet.ZooKeeper("xxx.xxx.xxx.xxx:2181,xxx.xxx.xxx.xxx:2182,xxx.xxx.xxx.xxx:2183", TimeSpan.FromSeconds(50), new MyWatcher()))
                {
                    //注意,当第一次调用命令时,Zookeeper可能还未连接到服务器。此时是调用命令会提示ZooKeeperNet.KeeperException.ConnectionLossException错误,所以要当收到服务器第1次返回SyncConnected给MyWatcher时,再开始往下执行代码,或者判断State再往下走。
                    while (zk.State != ZooKeeper.States.CONNECTED)
                    {
                        Thread.Sleep(100);
                        Console.WriteLine("Connect ...");
                    }
                    Org.Apache.Zookeeper.Data.Stat stat = zk.Exists("/root", true);//使用 exists 函数时,如果节点不存在将返回一个 null 值。
                    if (stat != null)
                    {
                        //删除前,要先删除子节点。
                        var nodes = zk.GetChildren("/root", false);
                        foreach (var item in nodes)
                        {
                            zk.Delete(string.Format("/root/{0}", item), -1);
                        }
                        zk.Delete("/root", -1);//前一个参数代表节点名称(一般用作路径),后一个是版本号 -1表示全匹配
                    }
    
                    Console.WriteLine("Begin Create Node");
                    String createResult = zk.Create("/root", "Song".GetBytes(), Ids.OPEN_ACL_UNSAFE, CreateMode.Persistent);//在创建节点的时候,需要提供节点的名称、数据、权限以及节点类型。
                    Console.WriteLine("Create Node Success:" + createResult);//return '/root'
    
    
                    Console.WriteLine("Begin Get Data");
                    var bys = zk.GetData("/root", true, null);
                    Console.WriteLine("Get Data Success:" + Encoding.UTF8.GetString(bys));//return 'Song' 
    
                    Console.WriteLine("Begin Update Data");
                    var statSet = zk.SetData("/root", "Sindrol".GetBytes(), -1);//数据量应为1MB以下。
                    if (statSet != null) Console.WriteLine("Update data Success!");
    
                    Console.WriteLine("Create data Sequential.");
                    zk.Create("/root/", "data1".GetBytes(), Ids.OPEN_ACL_UNSAFE, CreateMode.PersistentSequential); //路径中使用/结尾,则创建节点时当CreateMode.*Sequential时,会以数字序列形式生成子节点。
                    zk.Create("/root/", "data2".GetBytes(), Ids.OPEN_ACL_UNSAFE, CreateMode.PersistentSequential);
    
                    Console.WriteLine("Get Children:");
                    IEnumerable<string> lst = zk.GetChildren("/root", true).ToList().ConvertAll(s => "/root/" + s);
                    if (lst != null) Console.WriteLine("Get Children Success:" + string.Join(",", lst));
    
                    Console.WriteLine("Get Children Data:");
                    foreach (var item in lst)
                    {
                        var path = item;
                        var dataBys = zk.GetData(path, true, null);
                        Console.WriteLine(Encoding.UTF8.GetString(dataBys));
                    }
                }
            }
        }
    }

      好了,上面的代码就不多解释了,是最简单的了,和原生API也是很像的。

    四、使用zkCli命令行工具

      1、在zookeeper安装包解压目录下执行下列命令连接到Zookeeper并进入命令行模式,输入quit退出。

    ./bin/zkCli.sh -server 127.0.0.1:2181
    ./bin/zkCli.sh -server 127.0.0.1:2182
    ./bin/zkCli.sh -server 127.0.0.1:2183

      2、命令行操作:

     五、说明

      Zookeeper集群操作时,当Set数据时,它会同时给所有的服务器设置相同的数据,保证数据一致性,内存中Zookeeper会维护一个Linux结构的树型目录。设置数据时,数量量最大是1MB,不要太多。

  • 相关阅读:
    使用公钥登录SSL
    javascript看你能够做对几题
    windows 与fedora时间差
    Linux 启动直接进入 console,
    fedora -- java多版本切换
    fedora 解决yumBackend.py进程CPU占用过高
    fedora 禁止nouveau加载
    联邦学习中的隐私研究
    优秀博客链接
    【论文学习11】GIANT: Globally Improved Approximate Newton Method for Distributed Optimization
  • 原文地址:https://www.cnblogs.com/songxingzhu/p/9329647.html
Copyright © 2020-2023  润新知