Redis Clusterを動かしてみよう

## Redis Clusterとは？

Redis Clusterとは、Redisインスタンスを複数組み合わせることによってシャーディング(水平分割)やレプリケーション(複製)を行う技術のこと。
* Redisインスタンス一つをノードと呼ぶ。
* 0番~16383番まで存在するSlotをN分割し、それぞれのシャードに割り当てるシャーディング(水平分割)を行う。
* それぞれのシャードには書き込み可能なマスターノードと読み取り専用のスレーブノードの二種類を割り当てることができ、可用性を高めることができる。

## 作ってみよう

以下のようなdocker-composeファイルを作成する。redis1からredis6までの6つのサービスを用意した。

```yml:docker-compose.yml
version: '3.7'
services:
  redis1:
    image: redis

    volumes:
      - "./redis1:/etc/redis"
    command: "/etc/redis/redis.conf"
  redis2:
    image: redis
    volumes:
      - "./redis2:/etc/redis"      
    command: "/etc/redis/redis.conf"
  redis3:
    image: redis
    volumes:
      - "./redis3:/etc/redis"      
    command: "/etc/redis/redis.conf"
  redis4:
    image: redis
    volumes:
      - "./redis4:/etc/redis"      
    command: "/etc/redis/redis.conf"
  redis5:
    image: redis
    volumes:
      - "./redis5:/etc/redis"      
    command: "/etc/redis/redis.conf"
  redis6:
    image: redis
    volumes:
      - "./redis6:/etc/redis"      
    command: "/etc/redis/redis.conf"
```

それぞれが指定する```redis.conf```として、同じディレクトリに```redis1/redis.conf``` ```redis2/redis.conf``` ```redis3/redis.conf``` ```redis4/redis.conf``` ```redis5/redis.conf``` ```redis6/redis.conf```を用意する。

それぞれの内容は共通で以下のものとする。```cluster-enabled```とポート番号だけ指定した。

```conf:redis.conf
cluster-enabled yes
port 6379
```
ここまで用意したので、```docker-compose```を実行してみる。
```
docker compose up -d
```
これで6つ分のredisインスタンスが立った。これらをRedis-cluster化したいが、それぞれのIPアドレスを指定する必要がある。```dig```を用いて取得する。どれか一つのbashから、以下のコマンドを実行する。

```
apt-get update
apt install dnsutils
seq 1 6 | xargs -i dig redis{} | grep redis
```
これで以下のような出力が得られる。

```
; <<>> DiG 9.16.27-Debian <<>> redis1
;redis1.                                IN      A
redis1.                 600     IN      A       172.27.0.4
; <<>> DiG 9.16.27-Debian <<>> redis2
;redis2.                                IN      A
redis2.                 600     IN      A       172.27.0.6
; <<>> DiG 9.16.27-Debian <<>> redis3
;redis3.                                IN      A
redis3.                 600     IN      A       172.27.0.7
; <<>> DiG 9.16.27-Debian <<>> redis4
;redis4.                                IN      A
redis4.                 600     IN      A       172.27.0.5
; <<>> DiG 9.16.27-Debian <<>> redis5
;redis5.                                IN      A
redis5.                 600     IN      A       172.27.0.2
; <<>> DiG 9.16.27-Debian <<>> redis6
;redis6.                                IN      A
redis6.                 600     IN      A       172.27.0.3
```
これを用いてRedis Cluster作成を指定する。
```
redis-cli --cluster create 172.27.0.5:6379 172.27.0.7:6379 172.27.0.3:6379 172.27.0.4:6379 172.27.0.6:6379 172.27.0.2:6379
```

この状態だと、以下のような指定がされる。

```
Master[0] -> Slots 0 - 2730
Master[1] -> Slots 2731 - 5460
Master[2] -> Slots 5461 - 8191
Master[3] -> Slots 8192 - 10922
Master[4] -> Slots 10923 - 13652
Master[5] -> Slots 13653 - 16383
M: 825509db68aa9f08ef94e50dc8fde3292df48792 172.27.0.5:6379
   slots:[0-2730] (2731 slots) master
M: 5e0f25f4d77ec190cce3cd31cd5e6b6634572d83 172.27.0.7:6379
   slots:[2731-5460] (2730 slots) master
M: a41e612e80b1050d27bc962a12472b9ca0503eaf 172.27.0.3:6379
   slots:[5461-8191] (2731 slots) master
M: 1b704bc2d6e0d956253a4ba684cf0c82c833fc45 172.27.0.4:6379
   slots:[8192-10922] (2731 slots) master
M: bbb821b88d4b6de154eff17d289e810360e859ff 172.27.0.6:6379
   slots:[10923-13652] (2730 slots) master
M: 775fc4dcece3930993c000b3d04034f6685d0a92 172.27.0.2:6379
   slots:[13653-16383] (2731 slots) master
```

6個のノードで0-16383のスロットが分割されている。この6個はすべてマスターノードとなる。

これをキャンセルし、今度は、```--cluster-replicas 1```オプションを加えてみよう。

```
redis-cli --cluster create 172.27.0.5:6379 172.27.0.7:6379 172.27.0.3:6379 172.27.0.4:6379 172.27.0.6:6379 172.27.0.2:6379 --cluster-replicas 1
```
ここから以下のような指定が行われる。
```
Master[0] -> Slots 0 - 5460
Master[1] -> Slots 5461 - 10922
Master[2] -> Slots 10923 - 16383
Adding replica 172.27.0.6:6379 to 172.27.0.5:6379
Adding replica 172.27.0.2:6379 to 172.27.0.7:6379
Adding replica 172.27.0.4:6379 to 172.27.0.3:6379
M: 825509db68aa9f08ef94e50dc8fde3292df48792 172.27.0.5:6379
   slots:[0-5460] (5461 slots) master
M: 5e0f25f4d77ec190cce3cd31cd5e6b6634572d83 172.27.0.7:6379
   slots:[5461-10922] (5462 slots) master
M: a41e612e80b1050d27bc962a12472b9ca0503eaf 172.27.0.3:6379
   slots:[10923-16383] (5461 slots) master
S: 1b704bc2d6e0d956253a4ba684cf0c82c833fc45 172.27.0.4:6379
   replicates a41e612e80b1050d27bc962a12472b9ca0503eaf
S: bbb821b88d4b6de154eff17d289e810360e859ff 172.27.0.6:6379
   replicates 825509db68aa9f08ef94e50dc8fde3292df48792
S: 775fc4dcece3930993c000b3d04034f6685d0a92 172.27.0.2:6379
   replicates 5e0f25f4d77ec190cce3cd31cd5e6b6634572d83
```
今度は三つのマスターノードによってスロットが3分割され、残りの三つがスレーブノードとして対応するマスターノードの複製をされた。