Master具体细分为系统配置及监控加载模块、请求及相应封装处理模块、统计模块、监控及负载均衡等模块。具体的关系图如下:
图2.1 Master系统逻辑框架图
下面逐个对这些模块及主要代码进行分析讲解。
2.1 系统配置及监控加载模块
由于系统需要在启动的时候加载一些配置和监控模块,同时还需要在最后做一些系统的资源释放和销毁动作,加上spring提供了类似的重写接口,所以系统的入口类需要实现如下三个接口:ApplicationContextAware,InitializingBean,DisposableBean,实现如下:
/*
* (non-Javadoc)
*
* @see org.springframework.beans.factory.DisposableBean#destroy()
*/
public void destroy() throws Exception {
MasterCfgManager.destory();
}
/*
* (non-Javadoc)
*
* @see
* org.springframework.beans.factory.InitializingBean#afterPropertiesSet()
*/
public void afterPropertiesSet() throws Exception {
MasterCfgManager.init();
}
/*
* (non-Javadoc)
*
* @see
* org.springframework.context.ApplicationContextAware#setApplicationContext
* (org.springframework.context.ApplicationContext)
*/
public void setApplicationContext(ApplicationContext applicationContext)
throws BeansException {
WebAppContextUtil.setAppContext(applicationContext);
}
afterPropertiesSet在这个方法中主要是在spring对系统上下文加载完成之后会直接触发调用,系统的初始化就此开始。setApplicationContext这个方法主要是加载在spring中定义的类,用于系统master中加载对index和query分开处理的provider。接下来看下系统init中都加载了什么内容。
具体的初始化函数如下:
/**
* 初始化函数
*/
public static void init() {
loadCfg();
initSlaveClientPool();
initIndexPool();
initSearchPool();
initStatisticPool();
initParam();
ChameleonKeeperThreadPoolManager.init();
startChameleonKeeper();
registerZKRoot();
}
初始化主要是负责配置文件的加载,slave客户端restful调用的实例化类,初始化索引线程池和搜索线程池,以及master中需要用到的统计线程池,接下来就是启动一个zookeeperserver的守护线程,最后将master注册在zookeeper的一个root节点上,监听其下面的所有slaves端的节点信息变化。其中添加zookeeper server端的守护线程实现如下:
public static void startChameleonKeeper() {
ServerConfig config = loadServerConfig();
ChameleonKeeperThreadPoolManager
.addJobToZKServerStartExecutor(new ZKServerStartUpJob(config));
}
public static void addJobToZKServerStartExecutor(Runnable command) {
init();
DaemonThreadFactory daemon = new DaemonThreadFactory();
zkServerStartExecutor = daemon.newThread(command);
makeThreadName(zkServerStartExecutor,"-zkServerStartExecutor");
setUncaughtExceptionHandler(zkServerStartExecutor);
zkServerStartExecutor.start();
}
具体启动的线程run方法如下:
public void run() {
ZooKeeperServerMain main = new ZooKeeperServerMain();
try {
System.out.println("zookeeper server 启动");
main.runFromConfig(config);
System.out.println("zookeeper server 启动完成");
} catch (IOException e) {
LOG.error( "zookeeper server启动出错: " + e.getMessage() );
e.printStackTrace();
}
}
而监控zookeeper节点的创建如下:
public static void initZK(String server, String root) {
try {
if (zk == null || !zk.getState().isAlive()) {
synchronized (mutex) {
if (zk == null || !zk.getState().isAlive()) {
closeZK();
init(root);
createZK(server, root);
}
}
}
} catch (Exception e) {
e.printStackTrace();
LOG.error("init zk ConnectionLossException!", e);
}
}
private static void createZK(String server, String root) throws Exception {
zk = new ZooKeeper(server, sessionTimeOut, new ClientWatcher());
try {
Stat stat = zk.exists(root, false);
if (stat == null) {
zk.create(root, new byte[0], Ids.OPEN_ACL_UNSAFE,
CreateMode.PERSISTENT);
registerWatcher();
System.out.println("connect zk server success!");
}
} catch (KeeperException.ConnectionLossException e) {
System.out.println("ConnectionLoss exception sleep for 3s...");
Thread.sleep(3 * 1000);
System.out.println("connect zk server again");
createZK(server, root);
}
}
至此系统配置加载已经完成,同时对系统监控系统也已经启动完成,可以对slaves端的节点信息变化做出相应的处理。
循序渐进企业级搜索引擎之Master模块设计及实现-系统加载,布布扣,bubuko.com
循序渐进企业级搜索引擎之Master模块设计及实现-系统加载
原文:http://blog.csdn.net/letueodiandian/article/details/20788929