ZooKeeper简单案例-客户端请求,服务器响应

程序思路逻辑:
A.服务器代码:(可多线程同时上线多台服务器)
主函数
1.连接zookeeper
2.注册服务器
3.开始提供业务(无论请求是什么,都返回当前时间)
B.服务逻辑代码-实现-无论请求是什么,都返回当前时间
C.客户端
主函数
1.new一个自己的对象(客户端)
2.构造zk连接对象
3.查询在线服务器列表
4.处理业务(向一台服务器发送时间查询请求)

  1. 服务器代码
package cn.edu360.zk.gwtest;
import java.io.IOException;
import org.apache.zookeeper.CreateMode;
import org.apache.zookeeper.KeeperException;
import org.apache.zookeeper.ZooDefs.Ids;
import org.apache.zookeeper.ZooKeeper;
import org.apache.zookeeper.data.Stat;
import cn.edu360.zk.distributesystem.TimeQueryService;
public class TimerQuServer {
	ZooKeeper  zk = null;
	//连接zookeeper的方法
	public void getConnectZK() throws Exception{
		zk = new ZooKeeper("hdp01:2181,hdp02:2182,hdp03:2181", 2000, null);
	}
	
	//注册服务器的方法
	public void createServer(String hostname,String port) throws Exception{
		//判断当前服务器总目录,是否存在,如果不存在则创建
		Stat exists = zk.exists("/Servers", false);
		if(exists==null){
			zk.create("/Servers", "服务器总目录".getBytes(), Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);
		}
		//注册子服务器
			String server = zk.create("/Servers/Server", (hostname+":"+port).getBytes(), Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL_SEQUENTIAL);
		
			System.out.println("注册服务器成功,服务器地址:"+server);
		
	}
	
	
	
	//主函数
	//	1.连接zookeeper
	//  2.注册服务器
	//  3.开始提供业务
	public static void main(String[] args) {
		TimerQuServer timerQuServer = new TimerQuServer();
		
		try {
			timerQuServer.getConnectZK();
			timerQuServer.createServer(args[0], args[1]);		

			// 启动业务线程开始处理业务
			new TimeQueryService(Integer.parseInt(args[1])).start();
			
			
			
			
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
	}
	
}
  1. 服务逻辑代码
package cn.edu360.zk.gwtest;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Date;

public class TimerQuService extends Thread {
	//1 需要一个端口号 构造函数直接传
	int port = 0;

	public TimerQuService(int port) {
		this.port = port;
	}

	//重新run方法
	@Override
	public void run() {
		// TODO Auto-generated method stub

		try {
			//创建一个服务器对象
			ServerSocket socket = new ServerSocket(port);
			System.out.println("业务线程已绑定端口:"+port+"准备接受客户端请求");
			while(true){
				//等待接收客户端请求
				Socket accept = socket.accept();
				//获取客户端的情况
				InputStream in = accept.getInputStream();
				//发出给客户端的响应
				OutputStream out = accept.getOutputStream();
				//把当前时间转成byte写入响应
				out.write(new Date().toString().getBytes());		
				
			}			
			
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		
		
	}
	
	
}

  1. 客户端代码
package cn.edu360.zk.gwtest;

import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;

import org.apache.zookeeper.WatchedEvent;
import org.apache.zookeeper.Watcher;
import org.apache.zookeeper.ZooKeeper;
import org.apache.zookeeper.Watcher.Event.EventType;
import org.apache.zookeeper.Watcher.Event.KeeperState;

public class Client {
	//定义一个list 存放正在运行的服务器
	private volatile ArrayList onlineServers = new ArrayList();
	
	private ZooKeeper zk =null;
	
	//获取 zookeeper的连接
	public void getZKConn() throws Exception{
		zk = new ZooKeeper("hdp01:2181,hdp02:2181,hdp03:2181", 2000, new Watcher() {
			//重新监听进程
			@Override
			public void process(WatchedEvent event) {
				// TODO Auto-generated method stub
				//如果事件的状态=连接 且 事件的类型= 子节点变化 则重新或者online服务器
				
				
				
				
				
				
				
			   if (event.getState() == KeeperState.SyncConnected && event.getType() == EventType.NodeChildrenChanged) {
						//调用 更新 onlineServers
					try {
						System.out.println("*******************检查到服务器更新*********************");
						getOnlineServers();
					} catch (Exception e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
				}
			}
		});
	}
	
	
	//查询在线服务器列表
	public void getOnlineServers() throws Exception{
		//获取 servers下的所有child
		List childrens = zk.getChildren("/Servers", true);
		//这里需要新 new 一个list,然后复制后再覆盖 onlineServers
		ArrayList servers = new ArrayList();
		//循环所有child节点,
		for (String child : childrens) {
			//把服务器信息写入 onlineServers 中
			byte[] data = zk.getData("/Servers/"+child, false, null);
			
			servers.add(new String(data));	
			System.out.println("onlineServer更新"+new String(data));
		}
		onlineServers = servers;
	}
	
	
	
	//客户端请求方法
	@SuppressWarnings("resource")
	public void sendRequest() throws Exception{
		//随机挑选一台服务器
		Random random = new Random();
		while(true){
			
		
		int nextInt = random.nextInt(onlineServers.size());
		String targetServer = onlineServers.get(nextInt);
		
		System.out.println("本次的幸运儿服务器是:"+targetServer);
		
		//获取服务器端 和 口号
		String hostname = targetServer.split(":")[0];
		String port = targetServer.split(":")[1];
		
		//new 一个客户端
		Socket socket = new Socket(hostname,Integer.parseInt(port));
		
		//获取客户端的输入流与输出流
		OutputStream outputStream = socket.getOutputStream();
		InputStream inputStream = socket.getInputStream();
		
		//客户端发送输出流 给服务器
		outputStream.write("哥来发送请求了!".getBytes());
		outputStream.flush();
		
		//客户端获取服务器的输入流
		byte[] buf = new byte[256];//定一个字符
		int result = inputStream.read(buf);//把字符放到 buf  返回的 int对象为 读inputStream的结果
		System.out.println("服务器响应状态:+"+ result +" 服务器响应的时间为:" + new String(buf, 0, result));
		
		//一系列关闭
		outputStream.close();
		inputStream.close();
		socket.close();

		Thread.sleep(3000);
		}
	}
	
	
	
	//主函数
	public static void main(String[] args) throws Exception {
		
		//new一个自己的对象(客户端)
		Client client = new Client();
		
		// 构造zk连接对象
		client.getZKConn();
		
		// 查询在线服务器列表
		client.getOnlineServers();
		
		// 处理业务(向一台服务器发送时间查询请求)
		client.sendRequest();
		
	}
	
}

你可能感兴趣的:(hadoop)