2023.01.12

Redis cluster と Shard Pub/Sub のご紹介 ~Kubernetes 上に cluster を構築して Redis 機能を確認する~

次世代システム研究室の Y.I です。 今回は Redis についてまとめます。最近拝読した Redis の書籍が筆者の深い知識や経験が詰まった素晴らしい内容で、Redis についてキャッチアップし直しました。 GKE (GCP Kubernetes マネージドサービス) 上に Redis cluster を構築して、最新 Stable Version 7でリリースされた Shard Pub/Sub についてご紹介します。


Redis とは

Redis は多様な機能を持ったインメモリデータベースです。キャッシュ、Sorted Setによるリアルタイムランキング、PubSub、Shard PubSub、Stream機能などをもち、データベースとしてバックアップ/リカバリー、レプリケーション、cluster 機能もあります。

Redis cluster

Redis cluster は高可用性と書き込み性能を上げることができます。 マスターノードがダウンした際にも自動でレプリカノードがマスターへ昇格して、サービスを継続できます。 書き込み性能は、複数台のマスターを用意して cluster を構築することで、書き込み処理を各ノードで分散して行うことでスケールします。

構築

簡単に Redis cluster を構築するために、 GCP が提供してくれている構築scriptを利用します。 こちらを利用すると GKE (Kubernetesマネージドサービス) 上に Redis cluster を構築できます。今回はマスターノード3台レプリカノード3台の6台構成の cluster を構築します。

  • GKE 構築
  • gcloud container clusters create redis-cluster \
    --num-nodes 6 --machine-type n1-standard-1 \
    --disk-type pd-standard --disk-size 50 \
    --enable-ip-alias --create-subnetwork name=redis-subnet
    
  • GKE(Kubernetes) 構築結果
  • $ gcloud container clusters create redis-cluster \
    --num-nodes 6 --machine-type n1-standard-1 \
    --disk-type pd-standard --disk-size 50 \
    --enable-ip-alias --create-subnetwork name=redis-subnet
    Default change: During creation of nodepools or autoscaling configuration changes for cluster versions greater than 1.24.1-gke.800 a default location policy is applied. For Spot and PVM it defaults to ANY, and for all other VM kinds a BALANCED policy is used. To change the default values use the `--location-policy` flag.
    Note: The Pod address range limits the maximum size of the cluster. Please refer to https://cloud.google.com/kubernetes-engine/docs/how-to/flexible-pod-cidr to learn how to optimize IP address allocation.
    Creating cluster redis-cluster in asia-northeast1-b... Cluster is being health-checked (master is healthy)...done.
    Created [https://container.googleapis.com/v1/projects/jiken-dev-tokyo-research/zones/asia-northeast1-b/clusters/redis-cluster].
    To inspect the contents of your cluster, go to: https://console.cloud.google.com/kubernetes/workload_/gcloud/asia-northeast1-b/redis-cluster?project=jiken-dev-tokyo-research
    kubeconfig entry generated for redis-cluster.
    NAME           LOCATION           MASTER_VERSION  MASTER_IP     MACHINE_TYPE   NODE_VERSION    NUM_NODES  STATUS
    redis-cluster  asia-northeast1-b  1.24.7-gke.900  34.84.255.91  n1-standard-1  1.24.7-gke.900  6          RUNNING
    
  • Kubernetes 上に Redis cluster を構築
  • kubectl apply -f configmaps/
    # pod 起動
    kubectl apply -f redis-cache.yaml
    # pod IP取得
    kubectl get pods -l app=redis,redis-type=cache -o wide | tail -n +2 | awk '{printf "%s:%s ",$6,"6379"}' > redis-nodes.txt
    # Redis cluster構築スクリプトを配備
    kubectl create configmap redis-nodes --from-file=redis-nodes.txt
    # Redis culster 構築
    kubectl apply -f redis-create-cluster.yaml
    
  • Pod起動/Redis cluster 構築 結果
  • # kubernetes pod
    $ kubectl get pods
    W0111 16:42:25.235588   77674 gcp.go:119] WARNING: the gcp auth plugin is deprecated in v1.22+, unavailable in v1.26+; use gcloud instead.
    To learn more, consult https://cloud.google.com/blog/products/containers-kubernetes/kubectl-auth-changes-in-gke
    NAME                           READY   STATUS    RESTARTS   AGE
    redis-cache-5dc994ff6f-57gq5   1/1     Running   0          110s
    redis-cache-5dc994ff6f-j8x74   1/1     Running   0          110s
    redis-cache-5dc994ff6f-pknz4   1/1     Running   0          110s
    redis-cache-5dc994ff6f-qqzb2   1/1     Running   0          110s
    redis-cache-5dc994ff6f-rvg9p   1/1     Running   0          110s
    redis-cache-5dc994ff6f-wwhw6   1/1     Running   0          110s
    redis-create-cluster-2522x     1/1     Running   0          89s
    
    
    # Redis cluster node 確認
    /data # redis-cli -c -h localhost
    localhost:6379> cluster nodes
    d98ab5af5010e522587504f116693c96727175c3 10.42.28.8:6379@16379 myself,slave 0f4dc80f7445449a30daa4638a84f683d3635322 0 1673430697000 2 connected
    f5263432d2595bf22b74e89849ca2fc406de44d5 10.42.28.6:6379@16379 slave 6d5fe563e590859e4b2c7c7b2f801c77e51b110d 0 1673430697000 3 connected
    b87b1639fff2e3bda5975e9242d42f062aa5182e 10.42.28.7:6379@16379 slave 83bbf643a24924cc211e22ca5d558d33f1c9e005 0 1673430696000 1 connected
    6d5fe563e590859e4b2c7c7b2f801c77e51b110d 10.42.28.5:6379@16379 master - 0 1673430698205 3 connected 10923-16383
    83bbf643a24924cc211e22ca5d558d33f1c9e005 10.42.28.3:6379@16379 master - 0 1673430697200 1 connected 0-5460
    0f4dc80f7445449a30daa4638a84f683d3635322 10.42.28.4:6379@16379 master - 0 1673430696697 2 connected 5461-10922
    

    簡単に GKE 上に Redis cluster を構築できました。

    redis-cli クラスターモード

    MOVEDエラー回避のために、クラスターモードで Redis に接続しましょう。(redis-cli -c)

    Redis cluster は、保存するキーによって各マスターノードへ振り分けられます。16384個のスロットを各マスターへ分割して割り当てています。該当しないノードではそのキーをpubsubできないので、該当ノードへ接続する必要があります。その際、 redis-cli コマンドでは -c クラスターモードで接続することで自動で該当ノードへリダイレクトしてくれます。

    # ノード違い (MOVEDエラー)
    /data # redis-cli -h localhost
    localhost:6379> set key01 value01
    (error) MOVED 13770 10.42.28.5:6379    <= key01 のスロットは、10.42.28.5ノードが割り当てられている
    
    # 該当ノード (OK)
    localhost:6379> set key01 value01
    OK
    

    Shard PubSub

    Shard Pub/Sub とは、 Redis cluster 上で pubsub を行うときに効率的に pubsub を行える機能です。 通常の pubsub は全てのノードに対してメッセージを publish します。そのため publish 件数が多い状況だと Network や各ノードのCPU負荷が高まりやすくなります。 Shard pubsub はこちらの問題を解決する機能で、 該当のスロットを持っているノードのみへ publish してくれます。全ノードに送信しないので効率的に pubsub を実現できます。

    PubSub 動作確認

    全ノードへ送信する pubsub と 該当ノードだけに送信する Shard pubsub の事例

  • pubsub
  • # subscribe (受信)開始
    10.42.28.3:6379> subscribe channel:01
    
    # publish (送信)
    localhost:6379> publish channel:01 broadcast
    (integer) 0
    
    # subscribe (受信) ->全6ノードに同一メッセージがpublishされる
    10.42.28.3:6379> subscribe channel:01
    1) "message"
    2) "channel:01"
    3) "broadcast"
    
    10.42.28.5:6379> subscribe channel:01
    Reading messages... (press Ctrl-C to quit)
    1) "subscribe"
    2) "channel:01"
    3) (integer) 1
    ・・・
    
  • Shard pubsub
  • # ssubscribe (Shard 受信)開始 ->6台で別のchannelをsubscribe
    - channel:01 を受信
    10.42.28.3:6379> ssubscribe channel:01
    Reading messages... (press Ctrl-C to quit)
    -> Redirected to slot [12968] located at 10.42.28.5:6379
    Reading messages... (press Ctrl-C to quit)
    1) "ssubscribe"
    2) "channel:01"
    3) (integer) 1
    
    - channel:02 を受信
    10.42.28.5:6379> ssubscribe channel:02
    Reading messages... (press Ctrl-C to quit)
    -> Redirected to slot [715] located at 10.42.28.3:6379
    Reading messages... (press Ctrl-C to quit)
    1) "ssubscribe"
    2) "channel:02"
    3) (integer) 1
    ・・・
    
    # spublish (送信)  ->channel:01 のみへ
    
    localhost:6379> publish channel:01 
    (integer) 0
    
    # ssubscribe (受信) ->該当ノードのみにメッセージがpublishされる
    10.42.28.3:6379> ssubscribe channel:01
    ・・・
    1) "smessage"
    2) "channel:01"
    3) "Shard pubsub!"
    

    該当ノードのみへ publish されることを確認できました。


    参考

    Redis 公式

    Redis 公式

    書籍

    実践Redis入門 技術の仕組みから現場の活用まで

    GCP/Kubernetes script

    Deploying Redis Cluster on GKE

    最後に

    Redis cluster を簡単に構築できると Redis の機能を確認を簡単に試すことができて便利ですね。以前は Redis を用いてゲームPJでリアルタイムランキングを実現しましたが、多様な機能が実装されてますます便利なインメモリデータベースになっています。今後も採用事例が多くて開発が進んでいる Redis のキャッチアップを定期的に進めて行く予定です。

    一緒に働いてくれる方を募集中です!

    グループ研究開発本部では、グループ全体のインテグレーションを支援してくれるアーキテクトを募集しています。アプリケーション開発の方、次世代システム研究室にご興味を持って頂ける方がいらっしゃいましたら、ぜひ募集職種一覧からご応募をお願いします。

    • Twitter
    • Facebook
    • はてなブックマークに追加

    グループ研究開発本部の最新情報をTwitterで配信中です。ぜひフォローください。

     
    • AI研究開発室
    • 大阪研究開発グループ

    関連記事