linux中Zookeeper实战之选举

最近整理资料的时候发现了两年前自己写的一些Zookeeper的例子,今天整理了一下,放到这里,也许以后用的着。

首先准备一个Zookeeper集群环境,这里使用单机模拟集群环境,并使用代码方式启动服务。

Zookeeper服务

这里假定启动三个Zookeeper服务做集群

package my.zookeeperstudy;

import org.apache.commons.io.FileUtils;
import org.apache.zookeeper.server.quorum.QuorumPeerConfig;
import org.apache.zookeeper.server.quorum.QuorumPeerMain;

import java.io.File;
import java.net.InetAddress;
import java.util.Properties;

public class ZKServer {
    protected String id = null;
    protected String dataDir = null;
    protected String clientPort = null;

    public ZKServer(String id, String dataDir, String clientPort) {
        this.id = id;
        this.dataDir = dataDir;
        this.clientPort = clientPort;
    }

    public void startServer() {
        new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Properties props = new Properties();
                    props.setProperty("tickTime", "2000");
                    props.setProperty("dataDir", dataDir);
                    FileUtils.write(new File(props.getProperty("dataDir"), "myid"), id);
                    props.setProperty("clientPort", clientPort);
                    props.setProperty("initLimit", "10");
                    props.setProperty("syncLimit", "5");
                    String hostname = InetAddress.getLocalHost().getHostName();
                    props.setProperty("server.1", hostname + ":2881:3881");
                    props.setProperty("server.2", hostname + ":2882:3882");
                    props.setProperty("server.3", hostname + ":2883:3883");

                    QuorumPeerConfig quorumConfig = new QuorumPeerConfig();
                    quorumConfig.parseProperties(props);

                    QuorumPeerMain quorumPeerMain = new QuorumPeerMain();
                    quorumPeerMain.runFromConfig(quorumConfig);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }).start();
    }

}
package my.zookeeperstudy;

public class ZKServer1 {

    public static void main(String[] args) throws Exception {
        ZKServer zkServer = new ZKServer("1", "/tmp/zookeeper1/data", "2181");
        zkServer.startServer();
    }

}
package my.zookeeperstudy;

public class ZKServer2 {

    public static void main(String[] args) throws Exception {
        ZKServer zkServer = new ZKServer("2", "/tmp/zookeeper2/data", "2182");
        zkServer.startServer();
    }

}
package my.zookeeperstudy;

public class ZKServer3 {

    public static void main(String[] args) throws Exception {
        ZKServer zkServer = new ZKServer("3", "/tmp/zookeeper3/data", "2183");
        zkServer.startServer();
    }

}
测试客户端类

这里有三个客户端来模拟选举。

package my.zookeeperstudy.election;

import org.apache.zookeeper.*;

public class ZKClient {
    protected String id = null;
    protected String clientPort = null;
    protected String path = "/myapp_leader";

    public ZKClient(String id, String clientPort) {
        this.id = id;
        this.clientPort = clientPort;
    }

    protected void startClient() throws Exception {
        ZooKeeper zk = new ZooKeeper("localhost:" + clientPort, 10000,
                new Watcher() {
                    public void process(WatchedEvent event) {
                        System.out.println("event: " + event.getType());
                    }
                });

        while (true) {
            byte[] leader = null;
            try {
                leader = zk.getData(path, true, null);
            } catch(Exception e) {
                System.out.println("The leader is null.");
            }
            if (leader == null) {
                try {
                    zk.create(path, this.id.getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL);
                } catch(Exception e) {
                    // ignore me
                }
            } else {
                System.out.println("The leader is: " + new String(leader));
            }
            Thread.sleep(1 * 1000);
        }
    }
}
package my.zookeeperstudy.election;

public class ZKClient1 {

    public static void main(String[] args) throws Exception {
        ZKClient zkClient = new ZKClient("1", "2181");
        zkClient.startClient();
    }

}
package my.zookeeperstudy.election;

public class ZKClient2 {

    public static void main(String[] args) throws Exception {
        ZKClient zkClient = new ZKClient("2", "2182");
        zkClient.startClient();
    }

}
package my.zookeeperstudy.election;

public class ZKClient3 {

    public static void main(String[] args) throws Exception {
        ZKClient zkClient = new ZKClient("3", "2183");
        zkClient.startClient();
    }

}
测试

首先依次启动ZKServer1,ZKServer2和ZKServer3,启动过程会有错误,可以忽略,那是因为检测别的节点的时候连接失败导致,生产环境可以针对具体情况忽略此类错误。

然后依次启动ZKClient1,ZKClient2和ZKClient3。

分别观察三个Client日志输出。

停止当前选举到的leader,比如ZKClient1,然后观察日志输出,一段时间后会重新选举出一个leader。

时间: 2024-09-15 16:50:39

linux中Zookeeper实战之选举的相关文章

linux中Zookeeper实战之分布式锁示例

首先准备一个Zookeeper集群环境,这里使用单机模拟集群环境,并使用代码方式启动服务. Zookeeper服务 这里假定启动三个Zookeeper服务做集群 package my.zookeeperstudy; import org.apache.commons.io.FileUtils; import org.apache.zookeeper.server.quorum.QuorumPeerConfig; import org.apache.zookeeper.server.quorum.

Linux中环境变量文件及配置

一.环境变量文件介绍 转自:http://blog.csdn.net/cscmaker/article/details/7261921 Linux中环境变量包括系统级和用户级,系统级的环境变量是每个登录到系统的用户都要读取的系统变量,而用户级的环境变量则是该用户使用系统时加载的环境变量.所以管理环境变量的文件也分为系统级和用户级的,下面贴一个网上找到的讲的比较明白的文件介绍(略作修改)[1]: 1.系统级:(1)/etc/profile:该文件是用户登录时,操作系统定制用户环境时使用的第一个文件

10个重要的Linux ps命令实战

10个重要的Linux ps命令实战 Linux作为Unix的衍生操作系统,Linux内建有查看当前进程的工具ps.这个工具能在命令行中使用. PS 命令是什么 查看它的man手册可以看到,ps命令能够给出当前系统中进程的快照.它能捕获系统在某一事件的进程状态.如果你想不断更新查看的这个状态,可以使用top命令. ps命令支持三种使用的语法格式 UNIX 风格,选项可以组合在一起,并且选项前必须有"-"连字符 BSD 风格,选项可以组合在一起,但是选项前不能有"-"

详解Unix/Linux中周期执行指令Crontab命令_unix linux

简介 crontab命令常见于Unix和类Unix的操作系统之中,用于设置周期性被执行的指令.该命令从标准输入设备读取指令,并将其存放于"crontab"文件中,以供之后读取和执行. 通常,crontab储存的指令被守护进程激活,crond常常在后台运行,每一分钟检查是否有预定的作业需要执行.这类作业一般称为cron jobs. cron 是 Unix/Linux 中提供定期执行 shell 命令的服务,包括 crond 和 crontab 两部分:      crond: cron

Linux中select poll和epoll的区别

select的本质是采用32个整数的32位,即32*32= 1024来标识,fd值为1-1024.当fd的值超过1024限制时,就必须修改FD_SETSIZE的大小.这个时候就可以标识32*max值范围的fd. 对于单进程多线程,每个线程处理多个fd的情况,select是不适合的. 1.所有的线程均是从1-32*max进行扫描,每个线程处理的均是一段fd值,这样做有点浪费 2.1024上限问题,一个处理多个用户的进程,fd值远远大于1024 所以这个时候应该采用poll, poll传递的是数组头

linux中 shell 历史命令记录功能_Linux

在 Linux 下面可以使用 history 命令查看用户的所有历史操作,同时 shell 命令操作记录默认保存在用户目录的 .bash_history 文件中.通过这个文件可以查询 shell 命令的执行历史,有助于运维人员进行系统审计和问题排查,同时在服务器遭受黑客攻击后,也可以查询黑客登录服务器的历史命令操作.但是黑客在入侵后,为了抹除痕迹,会删除 .bash_history 文件,这个就需要合理备份这个文件了. 默认的 history 命令只能查看用户的历史操作记录,但是不能区分每个用户

Linux磁盘分区实战案例(必看篇)_Linux

一.查看新添加磁盘 [root@localhost /]# fdisk -l 磁盘 /dev/sda:53.7 GB, 53687091200 字节,104857600 个扇区 Units = 扇区 of 1 * 512 = 512 bytes 扇区大小(逻辑/物理):512 字节 / 512 字节 I/O 大小(最小/最佳):512 字节 / 512 字节 磁盘标签类型:dos 磁盘标识符:0x0009f1d1 设备 Boot Start End Blocks Id System /dev/s

linux中PHP dirname(

  在php 中dirname() 函数返回路径中的目录部分,__FILE__而当前运行文件的完整路径和文件名.如果用在被包含文件中,则返回被包含的文件名.这是一个魔法变量(预定义常量),在windows中没有问题但在linux中路径出现的问题,下面我们一起来看看路径问题解决方法. 近期在给wordpress开发模板功能时发现,直接使用include("文件名")的形式调用其他php代码片段时会出现路径错误.之前服务器环境一直都是iis,未曾出现过类似的BUG,但换成linux服务器后

linux中的"瑞士军刀"

linux中的"瑞士军刀" busybox 俗称linux中的瑞士军刀,它类似于linux系统中bash 的一个缩微版,常用于嵌入式设备中,例如你的android手机中等等.busybox作为一个开源的应用,它的解析命令行的应用是值得学习的 http://busybox.net/