package com.example.eurekaserver.zookeeper.leader;
import java.io.Serializable;
class Usercenter implements Serializable {
private static final long serialVersionUID = 448606814062626675L;
private int mc_id;
private String mc_name;
public int getMc_id() {
return mc_id;
}
public void setMc_id(int mc_id) {
this.mc_id = mc_id;
}
public String getMc_name() {
return mc_name;
}
public void setMc_name(String mc_name) {
this.mc_name = mc_name;
}
@Override
public String toString() {
return "Usercenter{" +
"mc_id=" + mc_id +
", mc_name='" + mc_name + '\'' +
'}';
}
}
package com.example.eurekaserver.zookeeper.leader;
//import com.example.eurekaserver.zookeeper.ZKClient;
import lombok.extern.slf4j.Slf4j;
import org.I0Itec.zkclient.IZkDataListener;
import org.I0Itec.zkclient.ZkClient;
import org.I0Itec.zkclient.exception.ZkNoNodeException;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
//zkclient
@Slf4j
public class MasterSelector {
private final static String MASTER_PATH = "/master";
public static boolean isRunning = false;
ScheduledExecutorService scheduledExecutorService =
Executors.newScheduledThreadPool(1);
private ZkClient zkClient;
private IZkDataListener dataListener;
private Usercenter master;
private Usercenter server;
public MasterSelector(Usercenter server, ZkClient zkClient) {
log.info("server {} 开始争抢master", server);
this.server = server;
this.zkClient = zkClient;
this.dataListener = new IZkDataListener() {
@Override
public void handleDataChange(String s, Object o) throws Exception {
}
@Override
public void handleDataDeleted(String s) throws Exception {
log.info("---触发删除事件:" + s);
chooseMaster();
}
};
}
private void chooseMaster() {
if (!isRunning) {
System.out.println("----isRunning=false 没有服务启动");
return;
}
try {
zkClient.createEphemeral(MASTER_PATH, server);
master = server;
log.info("-----chooseMaster::{}已经是master", master);
scheduledExecutorService.schedule(() -> {//每5s钟释放一次
log.info("----5s已经到时间,释放master");
releaseMaster();
}, 5, TimeUnit.SECONDS);
} catch (ZkNoNodeException e) {
//master已经存在
Usercenter usercenter =
zkClient.readData(MASTER_PATH,
true);
if (usercenter == null) {
chooseMaster();//再次获取master
} else {
master = usercenter;
}
e.printStackTrace();
}
}
private void releaseMaster() {
if (checkIsMaster()) {
log.info("----释放master::releaseMaster");
zkClient.deleteRecursive(MASTER_PATH);
}
}
private boolean checkIsMaster() {
Usercenter usercenter = zkClient.readData(MASTER_PATH);
if (usercenter.getMc_name().equals(server.getMc_name())) {
log.info("----检查是master");
master = usercenter;
return true;
}
return false;
}
public void start() {
if (!isRunning) {//如果未启动
log.info("-----开始选举::start----");
isRunning = true;
zkClient.subscribeDataChanges(MASTER_PATH, dataListener);
chooseMaster();
}
}
public void stop() {
if (isRunning) {
isRunning = false;
scheduledExecutorService.shutdown();
zkClient.unsubscribeDataChanges(MASTER_PATH, dataListener);
releaseMaster();
}
}
}
package com.example.eurekaserver.zookeeper.leader;
import org.I0Itec.zkclient.ZkClient;
import org.I0Itec.zkclient.serialize.SerializableSerializer;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;
public class SelectorTest {
private final static String CONNECTING="192.168.198.200:2181,192.168.198.201:2181," +
"192.168.198.202:2181";
public static void main(String [] args){
List<MasterSelector> masterSelectors=new ArrayList<>();
try {
for(int i=0;i<10;i++){
ZkClient zkClient=new ZkClient(CONNECTING,5000,
5000,
new SerializableSerializer());
Usercenter usercenter=new Usercenter();
usercenter.setMc_id(i);
usercenter.setMc_name("client:"+i);
MasterSelector selector=new MasterSelector(usercenter,zkClient);
masterSelectors.add(selector);
selector.start();//开始选举
TimeUnit.SECONDS.sleep(4);
}
}catch (InterruptedException e){
e.printStackTrace();
}finally {
for(MasterSelector masterSelector:masterSelectors){
masterSelector.stop();
}
}
}
}