Zookeeper 源码分析-启动
本文主要介绍了zookeeper启动的过程
运行zkServer.sh start命令可以启动zookeeper。入口的main函数在类中QuorumPeerMain。
main函数主要调用了runFromConfig函数,创建了QuorumPeer对象,并且调用了start函数,从而启动了zookeeper。
- public class QuorumPeerMain {
- protected QuorumPeer quorumPeer;
- /**
- * To start the replicated server specify the configuration file name on
- * the command line.
- * @param args path to the configfile
- */
- public static void main(String[] args) {
- QuorumPeerMain main = new QuorumPeerMain();
- main.initializeAndRun(args);
- }
- protected void initializeAndRun(String[] args)
- throws ConfigException, IOException
- {
- runFromConfig(config);
- }
- public void runFromConfig(QuorumPeerConfig config) throws IOException {
- LOG.info("Starting quorum peer");
- try {
- NIOServerCnxn.Factory cnxnFactory =
- new NIOServerCnxn.Factory(config.getClientPortAddress(),
- config.getMaxClientCnxns());
- quorumPeer = new QuorumPeer();
- quorumPeer.setClientPortAddress(config.getClientPortAddress());
- quorumPeer.setTxnFactory(new FileTxnSnapLog(
- new File(config.getDataLogDir()),
- new File(config.getDataDir())));
- quorumPeer.setQuorumPeers(config.getServers());
- quorumPeer.setElectionType(config.getElectionAlg());
- quorumPeer.setMyid(config.getServerId());
- quorumPeer.setTickTime(config.getTickTime());
- quorumPeer.setMinSessionTimeout(config.getMinSessionTimeout());
- quorumPeer.setMaxSessionTimeout(config.getMaxSessionTimeout());
- quorumPeer.setInitLimit(config.getInitLimit());
- quorumPeer.setSyncLimit(config.getSyncLimit());
- quorumPeer.setQuorumVerifier(config.getQuorumVerifier());
- quorumPeer.setCnxnFactory(cnxnFactory);
- quorumPeer.setZKDatabase(new ZKDatabase(quorumPeer.getTxnFactory()));
- quorumPeer.setLearnerType(config.getPeerType());
- quorumPeer.start();
- quorumPeer.join();
- } catch (InterruptedException e) {
- // warn, but generally this is ok
- LOG.warn("Quorum Peer interrupted", e);
- }
- }
- }
在QuorumPeer的start函数中,先调用了loadDataBase方法用于恢复数据。启动与client交互的线程,并
- @Override
- public synchronized void start() {
- try {
- zkDb.loadDataBase();
- } catch(IOException ie) {
- LOG.fatal("Unable to load database on disk", ie);
- throw new RuntimeException("Unable to run quorum server ", ie);
- }
- cnxnFactory.start(); //用于处理与client的交互
- startLeaderElection();//开始选举算法
- super.start();
- }
调用loadDatabase从磁盘加载数据到内存
- public long loadDataBase() throws IOException {
- PlayBackListener listener=new PlayBackListener(){
- public void onTxnLoaded(TxnHeader hdr,Record txn){
- Request r = new Request(null, 0, hdr.getCxid(),hdr.getType(),
- null, null);
- r.txn = txn;
- r.hdr = hdr;
- r.zxid = hdr.getZxid();
- addCommittedProposal(r);
- }
- };
- long zxid = snapLog.restore(dataTree,sessionsWithTimeouts,listener);
- initialized = true;
- return zxid;
- }
调用QuorumPeer的run函数,按照peer的state做不同的处理
- @Override
- public void run() {
- setName("QuorumPeer:" + cnxnFactory.getLocalAddress());
- try {
- /*
- * Main loop
- */
- while (running) {
- switch (getPeerState()) {
- case LOOKING:
- try {
- LOG.info("LOOKING");
- setCurrentVote(makeLEStrategy().lookForLeader());
- } catch (Exception e) {
- LOG.warn("Unexpected exception",e);
- setPeerState(ServerState.LOOKING);
- }
- break;
- case OBSERVING:
- try {
- LOG.info("OBSERVING");
- setObserver(makeObserver(logFactory));
- observer.observeLeader();
- } catch (Exception e) {
- LOG.warn("Unexpected exception",e );
- } finally {
- observer.shutdown();
- setObserver(null);
- setPeerState(ServerState.LOOKING);
- }
- break;
- case FOLLOWING:
- try {
- LOG.info("FOLLOWING");
- setFollower(makeFollower(logFactory));
- follower.followLeader();
- } catch (Exception e) {
- LOG.warn("Unexpected exception",e);
- } finally {
- follower.shutdown();
- setFollower(null);
- setPeerState(ServerState.LOOKING);
- }
- break;
- case LEADING:
- LOG.info("LEADING");
- try {
- setLeader(makeLeader(logFactory));
- leader.lead();
- setLeader(null);
- } catch (Exception e) {
- LOG.warn("Unexpected exception",e);
- } finally {
- if (leader != null) {
- leader.shutdown("Forcing shutdown");
- setLeader(null);
- }
- setPeerState(ServerState.LOOKING);
- }
- break;
- }
- }
- }
- }
- http://blog.csdn.net/xhh198781/article/details/10949697
Zookeeper 源码分析-启动的更多相关文章
- zookeeper源码分析之五服务端(集群leader)处理请求流程
leader的实现类为LeaderZooKeeperServer,它间接继承自标准ZookeeperServer.它规定了请求到达leader时需要经历的路径: PrepRequestProcesso ...
- zookeeper源码分析之四服务端(单机)处理请求流程
上文: zookeeper源码分析之一服务端启动过程 中,我们介绍了zookeeper服务器的启动过程,其中单机是ZookeeperServer启动,集群使用QuorumPeer启动,那么这次我们分析 ...
- zookeeper源码分析之三客户端发送请求流程
znode 可以被监控,包括这个目录节点中存储的数据的修改,子节点目录的变化等,一旦变化可以通知设置监控的客户端,这个功能是zookeeper对于应用最重要的特性,通过这个特性可以实现的功能包括配置的 ...
- Symfony2源码分析——启动过程2
文章地址:http://www.hcoding.com/?p=46 上一篇分析Symfony2框架源码,探究Symfony2如何完成一个请求的前半部分,前半部分可以理解为Symfony2框架为处理请求 ...
- quartz2.x源码分析——启动过程
title: quartz2.x源码分析--启动过程 date: 2017-04-13 14:59:01 categories: quartz tags: [quartz, 源码分析] --- 先简单 ...
- mysql源码分析-启动过程
mysql源码分析-启动过程 概要 # sql/mysqld.cc, 不包含psi的初始化过程 mysqld_main: // 加载my.cnf和my.cnf.d,还有命令行参数 if (load_d ...
- apiserver源码分析——启动流程
前言 apiserver是k8s控制面的一个组件,在众多组件中唯一一个对接etcd,对外暴露http服务的形式为k8s中各种资源提供增删改查等服务.它是RESTful风格,每个资源的URI都会形如 / ...
- storm操作zookeeper源码分析-cluster.clj
storm操作zookeeper的主要函数都定义在命名空间backtype.storm.cluster中(即cluster.clj文件中).backtype.storm.cluster定义了两个重要p ...
- Symfony2源码分析——启动过程1
本文通过阅读分析Symfony2的源码,了解Symfony2启动过程中完成哪些工作,从阅读源码了解Symfony2框架. Symfony2的核心本质是把Request转换成Response的一个过程. ...
随机推荐
- Google protobuf
个人理解: 定义.proto文件就是指明消息里包含的成员和类型,protoc会compile成相应的java文件包含interface和implementation class,然后在构建messag ...
- Oracle常用SQL语句
--2.查看表结构 desc wx_monitor_excption; --3.从表中查询数据 select * from wx_monitor_excption; --7.双引号保持原来的格式 se ...
- MVC 构造新Model实现内容搜索
当前在使用MVC开发一个网站,习惯了使用ASP.NET中控件,转到MVC之后突然对于页面和后台代码的传值感觉无从下手.花了点时间在网上看了写帖子后,想到了一个方法,重新构造一个新Model, 然后利用 ...
- String.Format 全汇总
C#格式化数值结果表 字符 说明 示例 输出 C 货币 string.Format("{0:C3}", 2) $2.000 D 十进制 string.Format("{0 ...
- Ubuntu Vim 复制到系统粘贴板
/************************************************************************* * Ubuntu Vim 复制到系统粘贴板 * 说 ...
- 《more effective c++》条款26 限制类对象的个数
问题: 如何限制类对象的个数?比如1个,10个等等. 方法(1): 将类的构造函数定义为private,那么就无法实例化这个类了.但是如何创建1个对象出来?方法有2种: 1.声明一个友元函数,那么在友 ...
- Vimium 快捷键记录
, <c-e> : Scroll down k, <c-y> : Scroll up h : Scroll left l : Scroll right gg : Scroll ...
- yii2构造方法
控制器文件下面建 一公共控制器:: CommonController.php 里面写一个空方法 : public function init(){} 然后在你要写构造函数的控制器类里写一个方法 ( ...
- WEBRTC源码片段分析(1)音频缓冲拷贝
源码位置webrtc/webrtc/modules/audio_device/ios/audio_device_ios.cc函数OSStatus AudioDeviceIPhone::RecordPr ...
- JavaScript学习记录总结(四)——js函数的特殊性
<script type="text/javascript"> //当局部变量与全局变量 重名的时候 var v="全局变量";//定义全局变 ...