Elasticsearchクラスタ環境を構築する

# はじめに

Elasticsearchクラスタ環境（3台）を構築します。
各サーバーはMasterノード、Dataノード、Ingestノードの役割を設定しますが、今回は3台と少ないので全てのサーバーで全ての役割を持たせます。

# 環境

使用した環境は以下のとおり。

- CentOS 7.5
- Elasticsearch 7.8.0
- Kibana 7.8.0

3台のサーバーはIPアドレスとホスト名は以下のとおりとします。

- elasticserver1(192.168.10.161)
- elasticserver2(192.168.10.162)
- elasticserver3(192.168.10.163)


# OpenJDKのインストール

まず、OpenJDK 8をインストールします。

```
# yum install -y java-1.8.0-openjdk-devel

# java -version
openjdk version "1.8.0_262"
OpenJDK Runtime Environment (build 1.8.0_262-b10)
OpenJDK 64-Bit Server VM (build 25.262-b10, mixed mode)
```

JAVA_HOMEを設定し、PATHにJavaのパスを追加しています。
※今回はJAVA_HOMEがなくても良いのですがお約束で設定。

```terminal
# echo "export JAVA_HOME=$(readlink -e $(which java)|sed 's:/bin/java::')" > /etc/profile.d/java.sh
# echo "PATH=\$PATH:\$JAVA_HOME/bin" >> /etc/profile.d/java.sh
# source /etc/profile
```


# Elasticsearchのインストール

以下の公式サイトのドキュメントを参照しインストールを実施していきます。

- [Get Elasticsearch up and running(公式サイト)](https://www.elastic.co/guide/en/elasticsearch/reference/current/getting-started-install.html)

以下のコマンドでElasticsearchをインストールします。

```
# curl -L -O https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-7.8.0-x86_64.rpm
# rpm -ivh elasticsearch-7.8.0-x86_64.rpm
```

Elasticsearchを外部からアクセスできるように設定します。

```
# vi /etc/elasticsearch/elasticsearch.yml
#network.host: 192.168.0.1
network.host: 0.0.0.0
```

クラスタ環境向けに以下の設定を追加で実施します。
以下はelasticserver1の場合で、他のサーバーの場合は最後の数値をインクリメントします。

```
cluster.name: mycluster
node.name: elasticserver1
transport.host: elasticserver1
discovery.seed_hosts:
  - "192.168.10.161"
  - "192.168.10.162"
  - "192.168.10.163"
cluster.initial_master_nodes:
  - "192.168.10.161"
  - "192.168.10.162"
  - "192.168.10.163"
```

自動起動するように設定し、起動まで実行します。

```
# systemctl enable elasticsearch
# systemctl start elasticsearch
```

最後に動作確認。

クラスターの状態を確認すると、以下のようになります。
number_of_nodesでノードが3つで、statusがgreenと表示されており正常に稼働していることが分かります。

```
# curl http://localhost:9200/_cluster/health?pretty
{
  "cluster_name" : "mycluster",
  "status" : "green",
  "timed_out" : false,
  "number_of_nodes" : 3,
  "number_of_data_nodes" : 3,
  "active_primary_shards" : 10,
  "active_shards" : 23,
  "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
}
```

また、次のコマンドでも確認できます。

```
# curl http://localhost:9200/_cat/nodes?v
ip             heap.percent ram.percent cpu load_1m load_5m load_15m node.role master name
192.168.10.161           35          66   3    0.03    0.33     0.28 dilmrt    *      elasticserver1
192.168.10.162           47          45   1    0.00    0.19     0.17 dilmrt    -      elasticserver2
192.168.10.163           23          45   1    0.13    0.27     0.18 dilmrt    -      elasticserver3
```

ログと設定ファイルは以下のディレクトリになります。

- /var/log/elasticsearch/
- /etc/elasticsearch/


# Kibanaのインストール

Elasticsearchのインストールが終わったら、次はKibanaをインストールします。

- [Install Kibana with RPM(公式サイト)](https://www.elastic.co/guide/en/kibana/current/rpm.html)

```
# wget https://artifacts.elastic.co/downloads/kibana/kibana-7.8.0-x86_64.rpm
# rpm -ivh kibana-7.8.0-x86_64.rpm
```

Kibanaを外部から接続できるように設定します。

```
# vi /etc/kibana/kibana.yml

#server.host: "localhost"
server.host: "0.0.0.0"
```

クラスター環境向けの設定では以下のようにElasticserverのアドレスを3台分設定します。

```
elasticsearch.hosts:
  - "http://elasticserver1:9200"
  - "http://elasticserver2:9200"
  - "http://elasticserver3:9200"
```

自動起動するように設定し、起動まで実行します。

```
# systemctl enable kibana
# systemctl start kibana
```

最後に動作確認。以下のURLをブラウザから開いて、Kibanaの画面が表示されることを確認します。

- http://[KibanaサーバーのIPアドレス]:5601


# 動作確認

シャード数が3、レプリケーションが2でインデックスを作成します。

```
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index?pretty -d '
{
    "settings": {
        "number_of_shards": 3,
        "index.number_of_replicas" : 2
    }
}'
```

次にドキュメントを5つほど登録してみます。

```
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index/_doc/1?pretty -d '{"id": 1, "hoge_field": "hoge1", "hoge_keyword" : "hoge_test"}'
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index/_doc/2?pretty -d '{"id": 2, "hoge_field": "hoge2", "hoge_keyword" : "hoge_test"}'
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index/_doc/3?pretty -d '{"id": 3, "hoge_field": "hoge3", "hoge_keyword" : "hoge_test"}'
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index/_doc/4?pretty -d '{"id": 4, "hoge_field": "hoge4", "hoge_keyword" : "hoge_test"}'
curl -H "Content-Type: application/json" -XPUT http://localhost:9200/hoge_index/_doc/5?pretty -d '{"id": 5, "hoge_field": "hoge5", "hoge_keyword" : "hoge_test"}'
```

cat shardsコマンドでインデックスのシャード・ドキュメント数などの情報を取得します。
サーバー(node)毎にシャードが3つあり、ドキュメントが登録されていることが確認できます。

```
# curl http://localhost:9200/_cat/shards/hoge_index?v
index      shard prirep state   docs store ip             node
hoge_index 1     p      STARTED    0  208b 192.168.10.161 elasticserver1
hoge_index 1     r      STARTED    3 4.4kb 192.168.10.162 elasticserver2
hoge_index 1     r      STARTED    3 4.4kb 192.168.10.163 elasticserver3
hoge_index 2     r      STARTED    1 4.3kb 192.168.10.161 elasticserver1
hoge_index 2     p      STARTED    0  208b 192.168.10.162 elasticserver2
hoge_index 2     r      STARTED    1 4.3kb 192.168.10.163 elasticserver3
hoge_index 0     r      STARTED    1 4.3kb 192.168.10.161 elasticserver1
hoge_index 0     r      STARTED    1 4.3kb 192.168.10.162 elasticserver2
hoge_index 0     p      STARTED    0  208b 192.168.10.163 elasticserver3
```

この状態でelasticserver3のプロセスをkillすると以下のようになります。
elasticserver3が表示されず、UNASSIGNEDになりました。

```
# curl http://localhost:9200/_cat/shards/hoge_index?v
index      shard prirep state      docs store ip             node
hoge_index 1     p      STARTED       0  208b 192.168.10.161 elasticserver1
hoge_index 1     r      STARTED       3 4.4kb 192.168.10.162 elasticserver2
hoge_index 1     r      UNASSIGNED                           
hoge_index 2     r      STARTED       1 4.3kb 192.168.10.161 elasticserver1
hoge_index 2     p      STARTED       0  208b 192.168.10.162 elasticserver2
hoge_index 2     r      UNASSIGNED                           
hoge_index 0     p      STARTED       1 9.9kb 192.168.10.161 elasticserver1
hoge_index 0     r      STARTED       1 4.3kb 192.168.10.162 elasticserver2
hoge_index 0     r      UNASSIGNED 
```

cat nodesコマンドを実行すると以下のように表示されます。

```
# curl http://localhost:9200/_cat/nodes?v
ip             heap.percent ram.percent cpu load_1m load_5m load_15m node.role master name
192.168.10.161           62          67   2    0.00    0.02     0.11 dilmrt    *      elasticserver1
192.168.10.162           52          45   2    0.00    0.01     0.07 dilmrt    -      elasticserver2
```

この状態でelasticserver2のプロセスをkillすると、1台だけとなり"master_not_discovered_exception"と表示されコマンドの実行に失敗するようになりました。

elasticserver3を起動すると以下のように結果が返ってきました。
全てのドキュメントがelasticserver2とelasticserver3に2つずつ登録されているようです。

```
# curl http://localhost:9200/_cat/shards/hoge_index?v
index      shard prirep state      docs  store ip             node
hoge_index 1     p      STARTED       3  6.1kb 192.168.10.161 elasticserver1
hoge_index 1     r      STARTED       3  6.1kb 192.168.10.163 elasticserver3
hoge_index 1     r      UNASSIGNED                            
hoge_index 2     p      STARTED       1 11.9kb 192.168.10.161 elasticserver1
hoge_index 2     r      STARTED       1  6.2kb 192.168.10.163 elasticserver3
hoge_index 2     r      UNASSIGNED                            
hoge_index 0     p      STARTED       1 10.1kb 192.168.10.161 elasticserver1
hoge_index 0     r      STARTED       1  5.9kb 192.168.10.163 elasticserver3
hoge_index 0     r      UNASSIGNED 
```

# 参考

- [Bootstrapping a cluster](https://www.elastic.co/guide/en/elasticsearch/reference/7.8/modules-discovery-bootstrap-cluster.html)
- [Discovery and cluster formation](https://www.elastic.co/guide/en/elasticsearch/reference/7.8/modules-discovery.html)