ES集群
节点
节点(node)是一个运行着的Elasticsearch实例,一个集群里面有多个ES的节点,一个集群通常会有一个主节点。
主节点的作用主要有两个:
一是做负载均衡,将请求均匀的转发到其他节点上。
二是存储其他节点必要的信息
每个节点都会存储其他节点的信息,一旦主节点宕机了,其他的节点中会选举一个节点当做主节点。
分片和副本
分片只是一个逻辑上的分区,用来存储数据。
当请求到来的时候数据会先经过主节点,把数据存贮在主节点上,然后将该数据复制一份存贮在复制分片上,这样就保证了数据有备份,即使某个ES节点宕机了,宕机ES的主分片不见了,那么其他的ES节点监控到有节点宕机,这是其他节点就会把宕机ES的主分片数据得备份拿出来,重新作为一个主分片。
我们的主分片和复制分片是在索引创建时指定的,一旦索引创建,主分片的个数就不能修改了
因为es的路由算法跟这个主分片的个数是有关系的,你修改了主分片的个数,数据就无法内部路由到正确位置,简单说就是数据查询不到了
实践
因为我们在window上测试,也不想麻烦弄什么vmware等虚拟机,所以下面实践我们会用伪集群的方式做部署实践
部署伪集群
下载es
# 这里我们部署3个节点: node1, node2, node3
# wget https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-6.2.2.zip
# 解压到x:\elk\Elasticsearch\cluster_test\elasticsearch-6.2.2-node1
# 然后我们copy2份, 你可以直接ctrl+C 然后改名即可
copy -r x:\elk\Elasticsearch\cluster_test\elasticsearch-6.2.2-node1 D:\elk\Elasticsearch\cluster_test\elasticsearch-6.2.2-node2
copy -r x:\elk\Elasticsearch\cluster_test\elasticsearch-6.2.2-node1 D:\elk\Elasticsearch\cluster_test\elasticsearch-6.2.2-node3
各节点的配置es
# elasticsearch-6.2.2-nodex\config\elasticsearch.yml
cluster.name: es-cluster
# 这里名字改成不同节点的名,我这边是node1, node2, node3
node.name: node1
network.host: 127.0.0.1
# 这里名字改成不同节点的名,我这边是node1->9201, node2->9202, node3->9203
# 这里名字改成不同节点的名,我这边是node1->9301, node2->9302, node3->9303
http.port: 9200
transport.tcp.port: 9301
discovery.zen.ping.unicast.hosts: ["127.0.0.1:9301", "127.0.0.1:9302", "127.0.0.1:9303"]
http.cors.enabled: true
http.cors.allow-origin: "*"
启动测试
# node1
xx/elasticsearch-6.2.2-node1/bin/elasticsearch.bat
# node2
xx/elasticsearch-6.2.2-node2/bin/elasticsearch.bat
# node3
xx/elasticsearch-6.2.2-node3/bin/elasticsearch.bat
查看集群健康
GET http://127.0.0.1:9201/_cluster/health?pretty
{
"cluster_name" : "es-cluster",
"status" : "green",
"timed_out" : false,
"number_of_nodes" : 3, //三个节点都正常启动了
"number_of_data_nodes" : 3,
"active_primary_shards" : 0,
"active_shards" : 0,
"relocating_shards" : 0,
"initializing_shards" : 0,
"unassigned_shards" : 0,
"delayed_unassigned_shards" : 0,
"number_of_pending_tasks" : 0,
"number_of_in_flight_fetch" : 0,
"task_max_waiting_in_queue_millis" : 0,
"active_shards_percent_as_number" : 100.0
}
随便一台安装head插件
# es 6.2.2版本es自带 需要独立安装
安装nodejs
下载https://github.com/coreybutler/nvm-windows 安装
nvm install v8.9.4
# npm加速 全局安装cnpm 指定来源淘宝镜像
npm install -g cnpm --registry=https://registry.npm.taobao.org
git clone git://github.com/mobz/elasticsearch-head.git
cd elasticsearch-head
cnpm install
修改head的端口
connect: {
server: {
options: {
port: 9101, //自行修改端口即可
base: '.',
keepalive: true
}
}
}
启动head
npm run start
创建一个索引
PUT http://localhost:9201/people
{
"settings" : {
"number_of_shards" : 3, //分配3个主分片
"number_of_replicas" : 1 //分配1个副本
}
}
# output
{
"acknowledged": true,
"shards_acknowledged": true,
"index": "people"
}
观察上次操作
左边节点:带星的标识是主节点,其他2个节点为普通节点
右边分片:边框带粗的是主分片,其他都是副本
本次我们发现我们每个还空了一个分片,未被利用
如果现在1个节点下线或出现故障,依然可以正常工作
如果现在2个节点下线或出现故障,就不能正常工作
再次创建一个索引
DELETE http://localhost:9201/people
# output
{
"acknowledged": true
}
PUT http://localhost:9201/people
{
"settings" : {
"number_of_shards" : 3, //分配3个主分片
"number_of_replicas" : 2 //分配1个副本
}
}
# output
{
"acknowledged": true,
"shards_acknowledged": true,
"index": "people"
}
观察上次操作
本次我们发现我们每一个节点都有一份完整的节点,只是带有主节点和副本节点而已
如果现在2个节点下线或出现故障,依然可以工作
动态调整副本
上一张我们是通过删除索引再创建,其实副本是可以动态调节的,不过主分片不能调整
我们来演示下
PUT http://localhost:9201/people/_settings
{
"number_of_replicas" : 1
}
# output
{
"acknowledged": true
}
# 既然操作后改回去哦 我们就是为了测试下说明下
插入测试
# 注意这里的连接的是9201
PUT http://localhost:9201/people/table1/1
{
"first_name" : "Douglas",
"last_name" : "Fir",
"age" : 35,
"about": "I like to build cabinets",
"interests": [ "forestry" ]
}
# 注意这里的连接的是9202
POST http://localhost:9202/people/_search
# output
{
"took": 81,
"timed_out": false,
"_shards": {
"total": 3,
"successful": 3,
"skipped": 0,
"failed": 0
},
"hits": {
"total": 1,
"max_score": 1,
"hits": [
{
"_index": "people",
"_type": "table1",
"_id": "1",
"_score": 1,
"_source": {
"first_name": "Douglas",
"last_name": "Fir",
"age": 35,
"about": "I like to build cabinets",
"interests": [
"forestry"
]
}
}
]
}
}
# 注意这里的连接的是9202
PUT http://localhost:9202/people/table1/1
{
"first_name" : "Douglas",
"last_name" : "Fir",
"age" : 35,
"about": "I like to build cabinets",
"interests": [ "music" ]
}
# output
{
"_index": "people",
"_type": "table1",
"_id": "1",
"_version": 2,
"result": "updated",
"_shards": {
"total": 2,
"successful": 2,
"failed": 0
},
"_seq_no": 1,
"_primary_term": 1
}
# 注意这里的连接的是9203
POST http://localhost:9203/people/_search
# output
{
"took": 6,
"timed_out": false,
"_shards": {
"total": 3,
"successful": 3,
"skipped": 0,
"failed": 0
},
"hits": {
"total": 1,
"max_score": 1,
"hits": [
{
"_index": "people",
"_type": "table1",
"_id": "1",
"_score": 1,
"_source": {
"first_name": "Douglas",
"last_name": "Fir",
"age": 35,
"about": "I like to build cabinets",
"interests": [
"music"
]
}
}
]
}
}
操作总结
我们可以发送请求到集群中的任一节点。 每个节点都有能力处理任意请求。 每个节点都知道集群中任一文档位置,所以可以直接将请求转发到需要的节点上。
ps: 当发送请求的时候, 为了扩展负载,更好的做法是轮询集群中所有的节点。
更多关于es的路由等参考
分布式文档存储
路由一个文档到一个分片中
主分片和副本分片如何交互
新建、索引和删除单个文档
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。