Solr cloud 系统结构及集群rebalance

1. 准备阶段

1.1. 基本概念

solr集群的概念可以参考 uc.cn 团队的一篇文章,写得很全面:

http://tech.uc.cn/?p=2387

 

1.2. rebalance概念

Rebalance有两个概念:

l   历史数据查询、更新,在solrcloud中要做到查询请求balance只需要保证索引数据均匀分布在集群的节点中;

l   新数据写入,在solrcloud中通过每个shard对应的range控制。

 

本文主要讨论对现有数据的rebalance,使用的策略比较简单,即保证数据平均分配,针对的是查询/更新请求。写入请求单独配置我还不太确定自己的理解是否正确。

 

 

2. 操作

2.1. 操作原理

solrcloud本身没有提供直接rebalance的接口,达到rebalance的方法比较麻烦,可参考 http://wiki.apache.org/solr/ZooKeeperIntegration#Rebalancing。大致的思路就是通过splitshard将原始shard一分为二,添加待转移sub shard的replica core,此replica core就是目标节点,当其为replica状态时会自动recovery leader中的数据,recovery结束后,删掉leader core,一个流程完毕。如果集群的节点较多,则需要通过不断重复上面的流程。

 

注意:如果是生产系统,操作过程中需要保证不要有新数据入库,否则可能造成数据不一致的问题。

2.2. 原始环境及目标

原始环境:

l   solr5.0 ,2 shards,1 replication

l   3节点

l   数据 36万

 

 

目标:

l   3 shards, 2 replication

 

 

2.3. 操作流程

2.3.1. 将其中一个shard切分为两个shard:

http://172.16.5.1:8983/solr/admin/collections?action=SPLITSHARD&collection=user&shard=shard1

操作的过程可能比较慢,如果抛出“splitshard the collection time out:300s”异常也美关系,后期线程还会继续运行。但是这个shard core的大小如果超过了那台机器的内存,那么split可能会失败!

 

切分完成后的效果,多出shard1_0和shard1_1:

 

 

此时这两个shard将会替代shard1进行工作,新数据会写到两个新的shard中,需要把原始shard删除,同时把相关的文件也删掉:

http://172.16.5.1:8983/solr/admin/cores?action=UNLOAD&core=user_shard1_replica1&deleteIndex=true&deleteDataDir=true&deleteInstanceDir=true&

 

2.3.2. 给需要移植到新服务器的shard增加replication

新的节点ip为172.16.5.4,操作地址:

http://172.16.5.4:8983/solr/admin/cores?wt=json&indexInfo=false&action=CREATE&name=user_shard1_1_replica2&instanceDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard1_1_replica2%2F&dataDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard1_1_replica2%2Fdata%2F&config=solrconfig.xml&schema=schema.xml&collection=user&shard=shard1_1&_=1427706027839

 

参数说明:

l   action=CREATE

l   name=user_shard1_1_replica2 :给这个新的core取名字,不要和集群中其它节点重复

l   instanceDir=/root/solr-5.0.0/server/solr/user_shard1_1_replica2/ :存放和此core相关配置文件的路径

l   dataDir=/root/solr-5.0.0/server/solr/user_shard1_1_replica2/data/ :存放此core数据的路径(注意:如果你的这个节点有多块硬盘,就可以在此处配置到其它路径下)

l   config=solrconfig.xml :solrconfig的文件名

l   schema=schema.xml :schema.xml的文件名

l   collection=user

l   shard=shard1_1 :原始shard名称

 

操作后集群状态:

 

 

注意172.16.5.4的状态是黄色的(recovering),此时正在从leader中同步数据,待确认数据同步完毕后,是可以删除leader的core的,至此shard split结束。

 

2.3.3. 确认数据同步完毕:

首先确认recovering结束:

 

 

对比两个core的数据大小,如下图查看numDocs数量:

 

 

 

2.3.4. 增加其它的replication,保证集群的稳定性

操作流程和上面的方式一致,增加剩余两个节点的replication:

l   http://172.16.5.4:8983/solr/admin/cores?wt=json&indexInfo=false&action=CREATE&name=user_shard2_replica2&instanceDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard2_replica2%2F&dataDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard2_replica2%2Fdata%2F&config=solrconfig.xml&schema=schema.xml&collection=user&shard=shard2&_=1427706027839

l   http://172.16.5.2:8983/solr/admin/cores?wt=json&indexInfo=false&action=CREATE&name=user_shard1_0_replica2&instanceDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard1_0_replica2%2F&dataDir=%2Froot%2Fsolr-5.0.0%2Fserver%2Fsolr%2Fuser_shard1_0_replica2%2Fdata%2F&config=solrconfig.xml&schema=schema.xml&collection=user&shard=shard1_0&_=1427706027839

 

完成后效果:

 

注意尽量保证每个shard都至少存在一份replication,两个节点不要重复同一个shard和replication。

 

2.3.5. 集群的节点在zookeeper中的状态:

位置:

 

 

数据:

 

{"user":{     "replicationFactor":"1",     "shards":{       "shard2":{         "range":"0-7fffffff",         "state":"active",         "replicas":{           "core_node1":{             "core":"user_shard2_replica1",             "base_url":"http://172.16.5.2:8983/solr",             {

    "user": {

        "replicationFactor": "1",

        "shards": {

            "shard2": {

                "range": "0-7fffffff",

                "state": "active",

                "replicas": {

                    "core_node1": {

                        "core": "user_shard2_replica1",

                        "base_url": "http://172.16.5.2:8983/solr",

                        "node_name": "172.16.5.2:8983_solr",

                        "state": "active",

                        "leader": "true"

                    },

                    "core_node6": {

                        "core": "user_shard2_replica2",

                        "base_url": "http://172.16.5.4:8983/solr",

                        "node_name": "172.16.5.4:8983_solr",

                        "state": "active"

                    }

                }

            },

            "shard1_0": {

                "parent": "shard1",

                "range": "80000000-bfffffff",

                "state": "active",

                "replicas": {

                    "core_node3": {

                        "core": "user_shard1_0_replica1",

                        "base_url": "http://172.16.5.1:8983/solr",

                        "node_name": "172.16.5.1:8983_solr",

                        "state": "active",

                        "leader": "true"

                    },

                    "core_node7": {

                        "core": "user_shard1_0_replica2",

                        "base_url": "http://172.16.5.2:8983/solr",

                        "node_name": "172.16.5.2:8983_solr",

                        "state": "active"

                    }

                }

            },

            "shard1_1": {

                "parent": "shard1",

                "range": "c0000000-ffffffff",

                "state": "active",

                "replicas": {

                    "core_node4": {

                        "core": "user_shard1_1_replica1",

                        "base_url": "http://172.16.5.1:8983/solr",

                        "node_name": "172.16.5.1:8983_solr",

                        "state": "active",

                        "leader": "true"

                    },

                    "core_node5": {

                        "core": "user_shard1_1_replica2",

                        "base_url": "http://172.16.5.4:8983/solr",

                        "node_name": "172.16.5.4:8983_solr",

                        "state": "active"

                    }

                }

            }

        },

        "router": {

            "name": "compositeId"

        },

        "maxShardsPerNode": "1",

        "autoAddReplicas": "false"

    }

}

 

3. 结束语

整体操作起来没有什么难度,步骤却很麻烦。在生产环境中尤其要注意监视每台服务器data目录的大小,一旦快要超过物理内存的大小,就应该是时候考虑split该shard了。

Zookeeper中得数据可以通过zk的客户端链接工具直接修改相关内容,比如solrconfig.xml或者schema.xml(修改完毕需要重启集群)。如果操作过程正中,不慎丢失state.json的range内容,也可以直接修改range的范围,但是切记不要算错了!

posted @ 2016-04-06 11:18  XGogo  阅读(567)  评论(0编辑  收藏  举报