K8s環境で本家のチュートリアルに従ってRabbitMQをデプロイしてみた
はじめに
Helmを利用してRabbitMQを稼動させていましたが、いろいろ問題が発生して、別クラスターを構築したタイミングで本家のドキュメントに従ってRabbitMQをK8s環境で稼動させてみました。
その際のメモを残します。
参考文書
- Deploying RabbitMQ to Kubernetes: What's Involved?
- Installing RabbitMQ Cluster Operator in a Kubernetes cluster
-
Using RabbitMQ Cluster Kubernetes Operator
環境
K8sクラスターは以下のような環境です。
- Hardware: TX1320 M4 (富士通製 Xeon E-2234)
- 8GB Memory (DDR4-21300 ECC)
- 4TB HDD (/dev/sda)
- 500GB SSD (/dev/sdb)
- K8s: v1.19.7 (Kubespray v2.15.0で構築)
- MetalLB v0.9.5 (Kubesprayのaddons.ymlで構成)
- Rook/Ceph v1.5.5
方針
今回はRabbitMQ Operatorを使用します。これはK8sのバージョンがv1.17以上、Dockerイメージが3.8.8以上という条件があって、以前構築したクラスターでは利用できないものでした。
本番に移行させることを目的に、テスト環境を構築したので、この手順を試してみることにします。
作業メモ
あらかじめRabbitMQ Cluster Operatorを導入しておきます。
$ sudo kubectl apply -f https://github.com/rabbitmq/cluster-operator/releases/latest/download/cluster-operator.yml
ここからの作業は参考文書に掲載したUsing RabbitMQ Cluster Kubernetes Operatorに従っていきます。
CRDsについて
Custom Resources (CRDs)を確認するよう指示があります。
$ sudo kubectl get crd/rabbitmqclusters.rabbitmq.com
NAME CREATED AT
rabbitmqclusters.rabbitmq.com 2021-01-26T05:59:59Z
確認するだけであればこれで十分ですが、どのようなCRDsが定義されているかは-o yaml
などの冗長出力によって確認することができます。
$ sudo kubectl get crd/rabbitmqclusters.rabbitmq.com -o yaml
長々と出力されますが定義されているリソースは、"RabbitmqCluster"だけのようです。
RabbitMQインスタンスの実行
書いてあるとおり、definition.yamlファイルを準備して適用します。
$ cat > 01.definition.yaml
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
$ sudo kubectl -n rabbitmq-system apply -f 01.definition.yaml
rabbitmqcluster.rabbitmq.com/definition created
$ sudo kubectl -n rabbitmq-system get all
NAME READY STATUS RESTARTS AGE
pod/definition-server-0 0/1 Pending 0 2s
pod/rabbitmq-cluster-operator-7bbbb8d559-884lc 1/1 Running 0 3h40m
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/definition ClusterIP 10.233.7.222 <none> 5672/TCP,15672/TCP 2s
service/definition-nodes ClusterIP None <none> 4369/TCP,25672/TCP 2s
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/rabbitmq-cluster-operator 1/1 1 1 3h40m
NAME DESIRED CURRENT READY AGE
replicaset.apps/rabbitmq-cluster-operator-7bbbb8d559 1 1 1 3h40m
NAME READY AGE
statefulset.apps/definition-server 0/1 2s
Podは現時点ではPendingのままです。原因についてはdescribeで確認します。
$ sudo kubectl -n rabbitmq-system describe pod definition-server-0
...
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Warning FailedScheduling 22h default-scheduler 0/3 nodes are available: 3 pod has unbound immediate PersistentVolumeClaims.
PVCを確認すると、次のようになっていました。
$ sudo kubectl -n rabbitmq-system get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
persistence-definition-server-0 Pending 10m
Pending状態の解消
PVはRook/Cephで構成しているために、PVC定義にstorageClassName: rook-ceph-block
を指定することが必要です。
RabbitMQのドキュメントにstorageClassNameを指定する方法が掲載されているので、これを参照し、01.definition.yamlを編集し、再度適用します。
$ cat 01.definition.yaml
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
spec:
persistence:
storageClassName: rook-ceph-block
storage: 20Gi
$ sudo kubectl -n rabbitmq-system delete -f 01.definition.yaml
$ sudo kubectl -n rabbitmq-system apply -f 01.definition.yaml
これで無事にサービスが起動するところまでは確認できました。
$ sudo kubectl -n rabbitmq-system get all
NAME READY STATUS RESTARTS AGE
pod/definition-server-0 0/1 Running 0 27s
pod/rabbitmq-cluster-operator-7bbbb8d559-884lc 1/1 Running 0 26h
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/definition ClusterIP 10.233.49.46 <none> 5672/TCP,15672/TCP 27s
service/definition-nodes ClusterIP None <none> 4369/TCP,25672/TCP 27s
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/rabbitmq-cluster-operator 1/1 1 1 26h
NAME DESIRED CURRENT READY AGE
replicaset.apps/rabbitmq-cluster-operator-7bbbb8d559 1 1 1 26h
NAME READY AGE
statefulset.apps/definition-server 0/1 27s
$ sudo kubectl -n rabbitmq-system get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
persistence-definition-server-0 Bound pvc-5cf12c25-aeb0-45f5-9ce6-b9825ec0946d 20Gi RWO rook-ceph-block 40s
LoadBalancerの有効化
このままだとサービスにWebブラウザからアクセスすることが難しいので、LoadBalancerを有効にします。
$ cat 01.definition.yaml
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
spec:
persistence:
storageClassName: rook-ceph-block
storage: 20Gi
service:
type: LoadBalancer
$ sudo kubectl -n rabbitmq-system apply -f 01.definition.yaml
rabbitmqcluster.rabbitmq.com/definition configured
$ sudo kubectl -n rabbitmq-system get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
definition LoadBalancer 10.233.49.46 192.168.1.110 5672:30104/TCP,15672:30706/TCP 59m
definition-nodes ClusterIP None <none> 4369/TCP,25672/TCP 59m
ドキュメントを眺める限りはLBにIPを割り当てるための設定(loadBalancerIP)がないようだと思って初稿を書いたのですが、spec.override.service が定義可能だと分かって次のような設定を試しました。
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
spec:
replicas: 3
persistence:
storageClassName: rook-ceph-block
storage: 20Gi
service:
type: LoadBalancer
override:
service:
spec:
loadBalancerIP: 192.168.1.139
この設定を適用すると、EXTERNAL-IPが指定した値になります。
EXTERNAL-IPを指定するもう一つの方法
このセクションは初稿でLoadBalancerにExternal-IPを割り当てる唯一の方法として記述したものです。オンプレミスであれば直接IPを指定する前述の方法が楽だと思いますが、環境に応じて使い分けてください。
annotationsに項目を追加することはできるので、address-poolを指定する方法で通常とは違うip-rangeを指定することはできそうです。
address-poolから割り当てられると、再構築したタイミングで変更されてしまう可能性があります。
サービス用のIPアドレスは固定したいので、loadBalancerIPを指定する以外の方法を検討します。
あらかじめmetallbの設定で、割り当てたいIPを別のpoolとして定義しておきます。
下記の例では元々設定していたip-rangeの最後の1つ(192.168.1.139)を"rabbitmq-pool"として別に定義しました。
今回のk8sクラスターではmetallbはkubesprayのaddons.ymlから設定しているので、あらかじめkubesprayからaddress-poolを追加しています。
$ sudo kubectl -n metallb-system get cm -o yaml
apiVersion: v1
items:
- apiVersion: v1
data:
config: |
address-pools:
- name: loadbalanced
protocol: layer2
addresses:
- 192.168.1.110-192.168.1.138
- name: rabbitmq-pool
protocol: layer2
addresses:
- 192.168.1.139-192.168.1.139
auto-assign: False
kind: ConfigMap
...
この"rabbitmq-pool"をannotationsで指定するよう01.definition.yamlファイルを編集し、適用します。
$ cat 01.definition.yaml
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
spec:
persistence:
storageClassName: rook-ceph-block
storage: 20Gi
service:
type: LoadBalancer
annotations:
metallb.universe.tf/address-pool: rabbitmq-pool
$ sudo kubectl -n rabbitmq-system apply -f 01.definition.yaml
rabbitmqcluster.rabbitmq.com/definition configured
設定が反映されると、1つしかIPが定義されていないrabbitmq-poolからEXTERNAL-IPが割り当てられた事を確認します。
$ sudo kubectl -n rabbitmq-system get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
definition LoadBalancer 10.233.18.226 192.168.1.139 15672:31925/TCP,5672:30675/TCP 14h
definition-nodes ClusterIP None <none> 4369/TCP,25672/TCP 36h
直接loadBalancerIPが割り当てられると良いのですが、これでも同じような事ができたので、しばらく使ってみます。
Web UIにログインするためのID,Passwordの確認
自動的にランダムな文字列が割り当てられているので、ログインに必要なID, Passwordをドキュメントに書かれているように確認します。
手元では次のようなMakefileのタスクを設定しています。
show-adminuser:
(i=`sudo kubectl -n rabbitmq-system get secret definition-default-user -o jsonpath="{.data.username}"
| base64 --decode | tee /dev/null` ; echo user: $$i)
(i=`sudo kubectl -n rabbitmq-system get secret definition-default-user -o jsonpath="{.data.password}"
| base64 --decode | tee /dev/null` ; echo pass: $$i)
Replica数の変更
デフォルトではPodが1つのRabbitMQクラスターとなっているので、複数のPodを実行します。
$ cat 01.definition.yaml
apiVersion: rabbitmq.com/v1beta1
kind: RabbitmqCluster
metadata:
name: definition
spec:
replicas: 3
persistence:
storageClassName: rook-ceph-block
storage: 20Gi
service:
type: LoadBalancer
annotations:
metallb.universe.tf/address-pool: rabbitmq-pool
これを適用し、コンソールからNodeが増加したことを確認します。
さいごに
Operatorによる制御はかなり自然で、今後はHelmからRabbitMQをデプロイすることはないと思います。
MetalLBではloadBalancerIPによる制御を許可すると、(管理下の)任意のIPアドレスがアサインできてしまうので管理面からはあらかじめ準備しているaddress-poolからEXTERNAL-IPを割り当てる方が実際の場面では便利なのかなと感じています。
更新した記事では、spec.override.service によるloadBalancerIPを使用する方法も確認しました。両方確認しましたが、address-poolを利用する方法もそれなりに便利だと利用してみて思っているところなので、環境に応じて適切なものを選択していこうと思います。
以上
Author And Source
この問題について(K8s環境で本家のチュートリアルに従ってRabbitMQをデプロイしてみた), 我々は、より多くの情報をここで見つけました https://qiita.com/YasuhiroABE/items/7c1e82e006ea37e0fe25著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .