文档章节

elasticsearch 源代码分析之Master选举

纳兰琴
 纳兰琴
发布于 2014/11/05 11:26
字数 923
阅读 1569
收藏 5

        ES 有Master节点和Data节点,Master节点什么意思呢? 就是主人节点,这个集群的主人,就是皇帝。ES同一时刻只有一个Master节点。小生一直看古装走火入魔,所谓心里有王朝,眼里就有王朝,看啥啥是王朝。就用王朝解释下集群,皇帝比喻下Master。我们先来看2个配置项。

  • node.master: true    就是 皇子,意思是有资格成为Master,成为皇帝的人选,这是天生的,是无字天书elasticsearch.yml里写好的。

  • discovery.zen.minimum_master_nodes:-1    就是几个皇子在场的时候,才能选新皇帝,不然难以服众,容易brain split是吧。

Master的职责

        只有皇帝才有资格发布圣旨ClusterState(集群状态)。他维护着这个王朝的状态,决定着这个王朝很多重要的大小事物。有一些事情必须皇帝才能执行,比如砍头(删除索引)。但是ES作为P2P集群,Master的职责,还是被弱化了一些。一张图看一下皇帝的工作内容。

什么时候选Master

        只有在皇帝驾崩,和王朝诞生的时候,才选举Master皇帝,是吧,想让皇帝禅位,除非他死了,或者王朝被推翻了(所有节点重启)

        节点启动,要加入一个集群的时候

//ZenDiscovery
private void innterJoinCluster() {
        boolean retry = true;
        while (retry) {
            if (lifecycle.stoppedOrClosed()) {
                return;
            }
            retry = false;
            DiscoveryNode masterNode = findMaster(); //找一个节点出来当皇帝
            if (masterNode == null) {
                logger.trace("no masterNode returned");
                retry = true;
                continue;
            }
            //....

        或者节点关闭 Master Gone

private void handleMasterGone(final DiscoveryNode masterNode, final String reason) {
 if (lifecycleState() != Lifecycle.State.STARTED) {
            return;
        }
        if (master) {
            return;
        }
        logger.info("master_left [{}], reason [{}]", masterNode, reason);
        clusterService.submitStateUpdateTask("zen-disco-master_failed (" + masterNode + ")", Priority.HIGH, new ProcessedClusterStateUpdateTask() {
            @Override
            public ClusterState execute(ClusterState currentState) {
                if (!masterNode.id().equals(currentState.nodes().masterNodeId())) {
                    return currentState;
                }
                DiscoveryNodes.Builder nodesBuilder = DiscoveryNodes.newNodesBuilder()
                        .putAll(currentState.nodes())
                        .remove(masterNode.id())
                        .masterNodeId(null);
                if (!electMaster.hasEnoughMasterNodes(nodesBuilder.build())) {
                    return rejoin(ClusterState.builder().state(currentState).nodes(nodesBuilder).build(), "not enough master nodes after master left (reason = " + reason + ")");
                }
                final DiscoveryNode electedMaster = electMaster.electMaster(nodesBuilder.build()); // 选举Master

Master选举

        首先必须是皇子(node.master: true),具体哪皇子成为皇帝呢? 看天意啊,最先启动的那个节点。老臣认为。当立嫡长子为太子,成为皇帝啊,这样江山社稷才能稳固啊,(一阵激动)省略上万句。。。好了,演完戏了,看代码。

ZenDiscovery模块启动的时候,要加入集群。findMaster 方法里,Ping一堆节点出来,Ping就是发现节点,这里的Ping不是Linux的命令Ping,是向ES的9300端口发送数据的意思。Linux的Ping是可以禁止的,不能因为命令Ping不通机器,就认为相互不能发现节点。Ping有组播MulticastZenPing和单播UnicastZenPing 两种。如果节点少,用单播也可以。组播在一些环境下可能无法相互发现节点,或者被安全软件识别为恶意程序。节点列表确定后。交给 ElectMasterService 去选举,快排后的第一个节点

    //ElectMasterService 
    /**
     * Elects a new master out of the possible nodes, returning it. Returns <tt>null</tt>
     * if no master has been elected.
     */
    public DiscoveryNode electMaster(Iterable<DiscoveryNode> nodes) {
        List<DiscoveryNode> sortedNodes = sortedMasterNodes(nodes);
        if (sortedNodes == null || sortedNodes.isEmpty()) {
            return null;
        }
        return sortedNodes.get(0);
    }

    private List<DiscoveryNode> sortedMasterNodes(Iterable<DiscoveryNode> nodes) {
        List<DiscoveryNode> possibleNodes = Lists.newArrayList(nodes);
        if (possibleNodes.isEmpty()) {
            return null;
        }
        // clean non master nodes
        for (Iterator<DiscoveryNode> it = possibleNodes.iterator(); it.hasNext(); ) {
            DiscoveryNode node = it.next();
            if (!node.masterNode()) {
                it.remove();
            }
        }
        CollectionUtil.quickSort(possibleNodes, nodeComparator);
        return possibleNodes;
    }

对了,皇帝上位以后,第一件事情是发布圣旨,昭告天下,以后寡人就是皇帝了。

怎么看,现在谁是皇帝呢?

curl http://localhost:9200/_cat/master?v


脑裂问题

        关于brain split脑裂问题,可以看这个,

  • 如何避免脑裂问题: http://blog.trifork.com/2013/10/24/how-to-avoid-the-split-brain-problem-in-elasticsearch/

  • 官方讨论:https://github.com/elasticsearch/elasticsearch/issues/2488

            

最后,为了让大家对皇帝有个感性的认识,赠图一张,不谢!

© 著作权归作者所有

纳兰琴
粉丝 51
博文 23
码字总数 13442
作品 0
杭州
高级程序员
私信 提问
加载中

评论(6)

各种打杂
各种打杂
给力,给力!!!!!!! 形象生动
timmy-duncan
timmy-duncan
楼主写的不错啊,诙谐幽默,又把原理给阐述清楚了。
timmy-duncan
timmy-duncan

引用来自“温佐镜”的评论

这样选主感觉有点简单,叫 paxos&raft情何以堪
请教一下,paxos&raft怎么选主?
温佐镜
温佐镜
这样选主感觉有点简单,叫 paxos&raft情何以堪
纳兰琴
纳兰琴 博主

引用来自“工力”的评论

证件给力
其实,文章也还行哈。没啥错别字
工力
工力
证件给力
elastic search+kibana 5.6.12安装指南

前提准备: 1,安装jdk, We recommend installing Java version 1.8.0_131 or later. 2, 设置文件最大打开数(使用命令ulimit -n查看) ulimit -n 65536 3, 创建用户elastic/用户组elastic gro...

PageYi
2018/10/23
293
0
Elastic 在年度用户大会 Elastic{ON} 2018 上发布众多新功能和技术预览

下载超过 2.25 亿次,Elastic 公开 X-Pack 源代码 旧金山 (Elastic{ON} 2018) – 2018 年 2 月 27 日 – Elastic,Elasticsearch 和 Elastic Stack背后的公司,今天宣布其产品累计下载次数达...

Medcl
2018/03/01
11
0
ELK 实验(六)elasticsearch集群搭建

本次实验使用3台虚拟机 192.168.209.168 192.168.209.169 192.168.209.170 cp /usr/elasticsearch-6.2.3/config/elasticsearch.yml /usr/elasticsearch-6.2.3/config/elasticsearch.yml.bak......

pcdog
2018/04/20
0
0
基于弹性堆栈(ELK堆栈)的日志分析、存储及展示

ELK简介 “ELK”是三个开源项目的首字母缩写:Elasticsearch,Logstash和Kibana。Elasticsearch是一个搜索和分析引擎。Logstash是一个服务器端数据处理管道,它同时从多个源中提取数据,对其...

cchenyz
2018/08/22
0
0
ElasticSearch大数据分布式弹性搜索引擎使用—从0到1

阅读目录: 背景 安装 下载elasticsearch servicewrapper 包 elasticsearch servicewrapper开源包的配置小bug servicewrapper安装 chkconfig -add 加入linux启动服务列表 查找、下载rpm包 、...

王清培
2018/06/26
0
0

没有更多内容

加载失败,请刷新页面

加载更多

微信公众号开发 (4) 网页授权

一、前言 微信公众号开发 (1) 微信接入认证成为开发者 微信公众号开发 (2) 消息处理 微信公众号开发 (3) 菜单处理 本文将实现 网页授权 获取用户基本信息 网页授权流程 填写网页授权回调域名...

郑清
31分钟前
29
0
号外!号外!百度语音开源库更新了

开源:ReactNative集成百度语音开源库,在这篇文章中作者开源了一个ReactNative集成百度语音合成的组件库,今天通过查看Github上的关于开源react-native-baidu-vtts 的issues,有朋友提到了一...

凌宇之蓝
37分钟前
141
1
【springcloud】之Eureka Server集群搭建

Eureka是微服务架构中的注册中心,专门负责服务的注册与发现 ,里面有一个注册表,保存了各服务所在的机器和端口号 下面我们开始配置 在这里,我配置了两个eureka server 1.新建springboot+...

西元yg
57分钟前
73
0
0120 springboot集成Mybatis和代码生成器

在日常开发中,数据持久技术使用的架子使用频率最高的有3个,即spring-jdbc , spring-jpa, spring-mybatis.详情可以看我之前的一篇文章spring操作数据库的3个架子 . spring-jdbc封装的比较少...

春天springcarter
58分钟前
131
0
re.search和re.match有什么区别?

Python re模块中的search()和match()函数有什么区别? 我已经阅读了文档 ( 当前文档 ),但是我似乎从未记得它。 我一直在查找并重新学习它。 我希望有人会用示例清楚地回答它,以便(也许)...

技术盛宴
58分钟前
57
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部