Hbase0.96源码之HMaster(二)Hmaster主要循环becomeActiveMaster
1,Hmaster主循环主要这里主要有:
1,1 becomeActiveMaster(startupStatus);
1.2 finishInitialization
1.3 loop()
becomeActiveMaster(startupStatus);
// We are either the active master or we were asked to shutdown
if (!this.stopped) {
finishInitialization(startupStatus, false);
loop();
}
2。becomeActiveMaster(startupStatus);
2.1.1首先创建一个ActiveMasterManager,负责watch zk上的事件,这里主要是nodeCreated()。nodeDeleted()
private boolean becomeActiveMaster(MonitoredTask startupStatus)
throws InterruptedException {
// TODO: This is wrong!!!! Should have new servername if we restart ourselves,
// if we come back to life.
//创建activeMasterManager对象
this.activeMasterManager = new ActiveMasterManager(zooKeeper, this.serverName,
this);
//注冊activeMasterManager到zk
this.zooKeeper.registerListener(activeMasterManager);
stallIfBackupMaster(this.conf, this.activeMasterManager);
// The ClusterStatusTracker is setup before the other
// ZKBasedSystemTrackers because it's needed by the activeMasterManager
// to check if the cluster should be shutdown.
this.clusterStatusTracker = new ClusterStatusTracker(getZooKeeper(), this);
this.clusterStatusTracker.start();
return this.activeMasterManager.blockUntilBecomingActiveMaster(startupStatus);
}
2.1.2 ActiveMasterManager上的事件处理这里不管是create还是都是delete节点都是一样的处
2.1.2.1 nodeCreated()与nodeDeleted事件处理
@Override
public void nodeCreated(String path) {
handle(path);
}
@Override
public void nodeDeleted(String path) {
if(path.equals(watcher.clusterStateZNode) && !master.isStopped()) {
clusterShutDown.set(true);
}
handle(path);
}
void handle(final String path) {
if (path.equals(watcher.getMasterAddressZNode()) && !master.isStopped()) {
handleMasterNodeChange();
}
}
2.1.2.2。终于的节点创建和删除处理函数,
2.1.2.2.1这里无论是创建还是删除节点都是同一处理函数,
2.1.2.2.2假设/hbase/master节点处在说明已经有active master了,
2.1.2.2.3另外这个 clusterHasActiveMaster.notifyAll();须要关注下,在后面的堵塞成为master会用到
private void handleMasterNodeChange() {
// Watch the node and check if it exists.
try {
synchronized(clusterHasActiveMaster) {
if (ZKUtil.watchAndCheckExists(watcher, watcher.getMasterAddressZNode())) {
// A master node exists, there is an active master
LOG.debug("A master is now available");
clusterHasActiveMaster.set(true);
} else {
// Node is no longer there, cluster does not have an active master
LOG.debug("No master available. Notifying waiting threads");
clusterHasActiveMaster.set(false);
// Notify any thread waiting to become the active master
clusterHasActiveMaster.notifyAll();
}
}
} catch (KeeperException ke) {
master.abort("Received an unexpected KeeperException, aborting", ke);
}
}
2.2堵塞成为master
boolean blockUntilBecomingActiveMaster(MonitoredTask startupStatus) {
while (true) {
startupStatus.setStatus("Trying to register in ZK as active master");
// Try to become the active master, watch if there is another master.
// Write out our ServerName as versioned bytes.
try {
//backupZNode -->/hbase/backup-masters/sn(hostname,port,startcode)
String backupZNode =
ZKUtil.joinZNode(this.watcher.backupMasterAddressesZNode, this.sn.toString());
// watcher.getMasterAddressZNode()-->/hbase/master
if (MasterAddressTracker.setMasterAddress(this.watcher,
this.watcher.getMasterAddressZNode(), this.sn)) {
// If we were a backup master before, delete our ZNode from the backup
// master directory since we are the active now)
if (ZKUtil.checkExists(this.watcher, backupZNode) != -1) {
LOG.info("Deleting ZNode for " + backupZNode + " from backup master directory");
ZKUtil.deleteNodeFailSilent(this.watcher, backupZNode);
}
// Save the znode in a file, this will allow to check if we crash in the launch scripts
ZNodeClearer.writeMyEphemeralNodeOnDisk(this.sn.toString());
// We are the master, return
startupStatus.setStatus("Successfully registered as active master.");
this.clusterHasActiveMaster.set(true);
LOG.info("Registered Active Master=" + this.sn);
return true;
}
// There is another active master running elsewhere or this is a restart
// and the master ephemeral node has not expired yet.
this.clusterHasActiveMaster.set(true);
/*
* Add a ZNode for ourselves in the backup master directory since we are
* not the active master.
*
* If we become the active master later, ActiveMasterManager will delete
* this node explicitly. If we crash before then, ZooKeeper will delete
* this node for us since it is ephemeral.
*/
LOG.info("Adding ZNode for " + backupZNode + " in backup master directory");
MasterAddressTracker.setMasterAddress(this.watcher, backupZNode, this.sn);
String msg;
byte[] bytes =
ZKUtil.getDataAndWatch(this.watcher, this.watcher.getMasterAddressZNode());
if (bytes == null) {
msg = ("A master was detected, but went down before its address " +
"could be read. Attempting to become the next active master");
} else {
ServerName currentMaster;
try {
currentMaster = ServerName.parseFrom(bytes);
} catch (DeserializationException e) {
LOG.warn("Failed parse", e);
// Hopefully next time around we won't fail the parse. Dangerous.
continue;
}
if (ServerName.isSameHostnameAndPort(currentMaster, this.sn)) {
msg = ("Current master has this master's address, " +
currentMaster + "; master was restarted? Deleting node.");
// Hurry along the expiration of the znode.
ZKUtil.deleteNode(this.watcher, this.watcher.getMasterAddressZNode());
// We may have failed to delete the znode at the previous step, but
// we delete the file anyway: a second attempt to delete the znode is likely to fail again.
ZNodeClearer.deleteMyEphemeralNodeOnDisk();
} else {
msg = "Another master is the active master, " + currentMaster +
"; waiting to become the next active master";
}
}
LOG.info(msg);
startupStatus.setStatus(msg);
} catch (KeeperException ke) {
master.abort("Received an unexpected KeeperException, aborting", ke);
return false;
}
synchronized (this.clusterHasActiveMaster) {
while (this.clusterHasActiveMaster.get() && !this.master.isStopped()) {
try {
this.clusterHasActiveMaster.wait();
} catch (InterruptedException e) {
// We expect to be interrupted when a master dies,
// will fall out if so
LOG.debug("Interrupted waiting for master to die", e);
}
}
if (clusterShutDown.get()) {
this.master.stop(
"Cluster went down before this master became active");
}
if (this.master.isStopped()) {
return false;
}
// there is no active master so we can try to become active master again
}
}
}
2.2.1 创建暂时节点/hbase/master,这里主要看
2.2.1.1
MasterAddressTracker.setMasterAddress(this.watcher,
this.watcher.getMasterAddressZNode(), this.sn)
2.2.1.2
public static boolean setMasterAddress(final ZooKeeperWatcher zkw,
final String znode, final ServerName master)
throws KeeperException {
return ZKUtil.createEphemeralNodeAndWatch(zkw, znode, toByteArray(master));
}
2.2.1.3,这里不论创建失败成功都会加入zkw事件watcher,成功则成为master。失败则可能是已经有master存在了
public static boolean createEphemeralNodeAndWatch(ZooKeeperWatcher zkw,
String znode, byte [] data)
throws KeeperException {
try {
zkw.getRecoverableZooKeeper().create(znode, data, createACL(zkw, znode),
CreateMode.EPHEMERAL);
} catch (KeeperException.NodeExistsException nee) {
if(!watchAndCheckExists(zkw, znode)) {
// It did exist but now it doesn't, try again
return createEphemeralNodeAndWatch(zkw, znode, data);
}
return false;
} catch (InterruptedException e) {
LOG.info("Interrupted", e);
Thread.currentThread().interrupt();
}
return true;
}
2.2.2假设失败则堵塞则
2.2.2.1
假设失败,说明不是active master,增加backup节点
LOG.info("Adding ZNode for " + backupZNode + " in backup master directory");
MasterAddressTracker.setMasterAddress(this.watcher, backupZNode, this.sn);
2.2.2.2 再次从zk获取master 的server地址。与自己比較。假设是则说明已经重新启动过
byte[] bytes =
ZKUtil.getDataAndWatch(this.watcher, this.watcher.getMasterAddressZNode());
if (bytes == null) {
msg = ("A master was detected, but went down before its address " +
"could be read. Attempting to become the next active master");
} else {
ServerName currentMaster;
try {
currentMaster = ServerName.parseFrom(bytes);
} catch (DeserializationException e) {
LOG.warn("Failed parse", e);
// Hopefully next time around we won't fail the parse. Dangerous.
continue;
}
if (ServerName.isSameHostnameAndPort(currentMaster, this.sn)) {
msg = ("Current master has this master's address, " +
currentMaster + "; master was restarted? Deleting node.");
// Hurry along the expiration of the znode.
ZKUtil.deleteNode(this.watcher, this.watcher.getMasterAddressZNode());
// We may have failed to delete the znode at the previous step, but
// we delete the file anyway: a second attempt to delete the znode is likely to fail again.
ZNodeClearer.deleteMyEphemeralNodeOnDisk();
} else {
msg = "Another master is the active master, " + currentMaster +
"; waiting to become the next active master";
}
2.2 堵塞在clusterHasActiveMaster,这里等待知道notify。由ActiveMasterManager(2.1.2)来触发
synchronized (this.clusterHasActiveMaster) {
while (this.clusterHasActiveMaster.get() && !this.master.isStopped()) {
try {
this.clusterHasActiveMaster.wait();
} catch (InterruptedException e) {
// We expect to be interrupted when a master dies,
// will fall out if so
LOG.debug("Interrupted waiting for master to die", e);
}
}
if (clusterShutDown.get()) {
this.master.stop(
"Cluster went down before this master became active");
}
if (this.master.isStopped()) {
return false;
}
// there is no active master so we can try to become active master again
}
Hbase0.96源码之HMaster(二)Hmaster主要循环becomeActiveMaster的更多相关文章
- Hbase0.96源码之HMaster(一)
从main()函数開始 public static void main(String [] args) { VersionInfo.logVersion(); new HMasterCommandLi ...
- Hbase0.96源码之HMaster(三)Hmaster主要循环
1.Master初始化 1.1 if (!this.stopped) { finishInitialization(startupStatus, false); loop(); } 1.2 finis ...
- 【原】FMDB源码阅读(二)
[原]FMDB源码阅读(二) 本文转载请注明出处 -- polobymulberry-博客园 1. 前言 上一篇只是简单地过了一下FMDB一个简单例子的基本流程,并没有涉及到FMDB的所有方方面面,比 ...
- 【原】AFNetworking源码阅读(二)
[原]AFNetworking源码阅读(二) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 上一篇中我们在iOS Example代码中提到了AFHTTPSessionMa ...
- 【原】SDWebImage源码阅读(二)
[原]SDWebImage源码阅读(二) 本文转载请注明出处 —— polobymulberry-博客园 1. 解决上一篇遗留的坑 上一篇中对sd_setImageWithURL函数简单分析了一下,还 ...
- YYModel 源码解读(二)之NSObject+YYModel.h (1)
本篇文章主要介绍 _YYModelPropertyMeta 前边的内容 首先先解释一下前边的辅助函数和枚举变量,在写一个功能的时候,这些辅助的东西可能不是一开始就能想出来的,应该是在后续的编码过程中 ...
- Cwinux源码解析(二)
我在我的个人博客上发表了第二篇解析文章.欢迎各位读者批评指正. Cwinux源码解析(二)
- DataTable源码分析(二)
DataTable源码分析(二) ===================== DataTable函数分析 ---------------- DataTable作为整个插件的入口,完成了整个表格的数据初 ...
- 一个普通的 Zepto 源码分析(二) - ajax 模块
一个普通的 Zepto 源码分析(二) - ajax 模块 普通的路人,普通地瞧.分析时使用的是目前最新 1.2.0 版本. Zepto 可以由许多模块组成,默认包含的模块有 zepto 核心模块,以 ...
随机推荐
- Linux目录结构和常用命令
源地址:http://www.cnblogs.com/JCSU/articles/2770249.html 一.Linux目录结构 你想知道为什么某些程序位于/bin下,或者/sbin,或者/usr/ ...
- 14.4.3.5 Configuring InnoDB Buffer Pool Flushing 配置InnoDB Buffer Pool 刷新:
14.4.3.5 Configuring InnoDB Buffer Pool Flushing 配置InnoDB Buffer Pool 刷新: InnoDB执行某些任务在后台, 包括flush 脏 ...
- 通过设置Referer反"反盗链"
package cn.searchphoto.util; import java.io.File; import java.io.FileOutputStream; import java.io.In ...
- Bootstrapping (compilers) - Wikipedia, the free encyclopedia
Bootstrapping (compilers) - Wikipedia, the free encyclopedia Bootstrapping (compilers)
- 计算机视觉与模式识别代码合集第二版three
计算机视觉与模式识别代码合集第二版three Topic Name Reference code Optical Flow Horn and Schunck's Optical Flow ...
- Python heapq 模块的实现 - A Geek's Page
Python heapq 模块的实现 - A Geek's Page Python heapq 模块的实现
- android之JSON 进行网络数据交换
什么是JSON JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,易于阅读和编写,同一时候也易于机器解析和生成,很适合于server与client的交互. J ...
- CentOS 6.5安装Erlang/OTP 17.0
CentOS 6.5安装Erlang/OTP 17.0 作者:chszs,转载需注明.博客主页:http://blog.csdn.net/chszs Erlang眼下已经是Fedora和Debian/ ...
- HDU 5107 线段树扫描线
给出N个点(x,y).每一个点有一个高度h 给出M次询问.问在(x,y)范围内第k小的高度是多少,没有输出-1 (k<=10) 线段树扫描线 首先离散化Y坐标,以Y坐标建立线段树 对全部的点和询 ...
- SVN最有效的方法打基线
笔者:张克强 在微博上:张克强-敏捷307 2014/7/6 方法一来自于我的一条微博: 组织级scm建一个名为controlled的文件夹,当项目某文档通过评审后,组织级scm从项目文件夹下找 ...