K8S部署RabbitMQ集群 (鏡像模式) - 部署筆記


 

RabbitMQ 簡介
以熟悉的電商場景為例,如果商品服務和訂單服務是兩個不同的微服務,在下單的過程中訂單服務需要調用商品服務進行扣庫存操作。按照傳統的方式,下單過程要等到調用完畢之后才能返回下單成功,如果網絡產生波動等原因使得商品服務扣庫存延遲或者失敗,會帶來較差的用戶體驗,如果在高並發的場景下,這樣的處理顯然是不合適的,那怎么進行優化呢?這就需要消息隊列登場了。
 
消息隊列提供一個異步通信機制,消息的發送者不必一直等待到消息被成功處理才返回,而是立即返回。消息中間件負責處理網絡通信,如果網絡連接不可用,消息被暫存於隊列當中,當網絡暢通的時候在將消息轉發給相應的應用程序或者服務,當然前提是這些服務訂閱了該隊列。如果在商品服務和訂單服務之間使用消息中間件,既可以提高並發量,又降低服務之間的耦合度。
 
RabbitMQ就是這樣一款我們苦苦追尋的消息隊列。RabbitMQ是一個開源的消息代理的隊列服務器,用來通過普通協議在完全不同的應用之間共享數據。
 
RabbitMQ 的特點
開源、性能優秀,速度快,穩定性保障提供可靠性消息投遞模式、返回模式與Spring AMQP完美整合,API豐富集群模式豐富,表達式配置,HA模式,鏡像隊列模型保證數據不丟失的前提做到高可靠性、可用性
 
RabbitMQ 典型應用場景
  • 異步處理:把消息放入消息中間件中,等到需要的時候再去處理。
  • 流量削峰:例如秒殺活動,在短時間內訪問量急劇增加,使用消息隊列,當消息隊列滿了就拒絕響應,跳轉到錯誤頁面,這樣就可以使得系統不會因為超負載而崩潰。
  • 日志處理;(不過一般日志處理都使用Kafka這種消息隊列)
  • 應用解耦:假設某個服務A需要給許多個服務(B、C、D)發送消息,當某個服務(例如B)不需要發送消息了,服務A需要改代碼再次部署;當新加入一個服務(服務E)需要服務A的消息的時候,也需要改代碼重新部署;另外服務A也要考慮其他服務掛掉,沒有收到消息怎么辦?要不要重新發送呢?是不是很麻煩,使用MQ發布訂閱模式,服務A只生產消息發送到MQ,B、C、D從MQ中讀取消息,需要A的消息就訂閱,不需要了就取消訂閱,服務A不再操心其他的事情,使用這種方式可以降低服務或者系統之間的耦合。
RabbitMQ集群節點之間是如何相互認證的:
  • 通過Erlang Cookie,相當於共享秘鑰的概念,長度任意,只要所有節點都一致即可。
  • rabbitmq server在啟動的時候,erlang VM會自動創建一個隨機的cookie文件。cookie文件的位置是/var/lib/rabbitmq/.erlang.cookie 或者 /root/.erlang.cookie,為保證cookie的完全一致,采用從一個節點copy的方式。
Erlang Cookie是保證不同節點可以相互通信的密鑰,要保證集群中的不同節點相互通信必須共享相同的Erlang Cookie。具體的目錄存放在/var/lib/rabbitmq/.erlang.cookie。
 
說明:這就要從rabbitmqctl命令的工作原理說起,RabbitMQ底層是通過Erlang架構來實現的,所以rabbitmqctl會啟動Erlang節點,並基於Erlang節點來使用Erlang系統連接RabbitMQ節點,在連接過程中需要正確的Erlang Cookie和節點名稱,Erlang節點通過交換Erlang Cookie以獲得認證。
 

RabbitMQ集群模式

  • 單機模式
  • 普通集群模式(無高可用性)
  • 鏡像集群模式(高可用性),最常用的集群模式。

 

RabbitMQ集群故障處理機制:
  • rabbitmq broker集群允許個體節點down機,
  • 對應集群的的網絡分區問題( network partitions)
RabbitMQ集群推薦用於LAN環境,不適用WAN環境;
要通過WAN連接broker,Shovel or Federation插件是最佳的解決方案;Shovel or Federation不同於集群。
 
 
RabbitMQ節點類型
  • RAM node:只保存狀態到內存。內存節點將所有的隊列、交換機、綁定、用戶、權限和vhost的元數據定義存儲在內存中,好處是可以使得像交換機和隊列聲明等操作更加的快速。
  • Disk node:將元數據存儲在磁盤中。單節點系統只允許磁盤類型的節點,防止重啟RabbitMQ的時候,丟失系統的配置信息。
內存節點雖然不寫入磁盤,但是它執行比磁盤節點要好。RabbitMQ集群中,只需要一個磁盤節點來保存狀態就足夠了;如果集群中只有內存節點,那么不能停止它們,否則所有的狀態,消息等都會丟失。
 
問題說明:
  • RabbitMQ要求在集群中至少有一個磁盤節點,所有其他節點可以是內存節點,當節點加入或者離開集群時,必須要將該變更通知到至少一個磁盤節點。
  • 如果集群中唯一的一個磁盤節點崩潰的話,集群仍然可以保持運行,但是無法進行其他操作(增刪改查),直到節點恢復。
解決方案:設置兩個磁盤節點,至少有一個是可用的,可以保存元數據的更改。
 
RabbitMQ集群的節點運行模式:
  • 為保證數據持久性,當前所有node節點跑在disk模式。
  • 如果今后壓力大,需要提高性能,考慮采用ram模式。
 
RabbitMQ集群記錄
本案例采用 "鏡像模式",即隊列為鏡像隊列,隊列消息存在集群的每個節點上。
 
1、版本說明
因為考慮到較早版本rabbitmq在k8s上的集群部署是使用autocluster插件去調用kubernetes apiserver來獲取rabbitmq服務的endpoints,進而獲取node節點信息,並自動加入集群,但是現在autocluster已不再更新了,並且只支持3.6.x版本,故而放棄這種方式。
 
對於3.7.x或更新的版本,現在市場主流是使用 peer discovery subsystem來構建rabbitmq-cluster, 參考這里
 
2、部署方式
在Kubernetes上搭建RabbitMQ有4種部署方法(IP模式、Pod與Server的DNS模式、Statefulset 與Headless Service模式、hostname模式),這里選擇StatefulSet與Headless Service模式部署有狀態的RabbitMQ集群。
 
3、使用NFS配置StatefulSet的動態持久化存儲
 
1)在NFS服務器端(172.16.60.238)通過nfs創建RabbitMQ集群的共享目錄
[root@k8s-harbor01 ~]# mkdir -p /data/storage/k8s/rabbitmq

  

2)創建nfs的rbac
[root@k8s-master01 ~]# mkdir -p /opt/k8s/k8s_project/rabbitmq
[root@k8s-master01 ~]# cd /opt/k8s/k8s_project/rabbitmq
[root@k8s-master01 rabbitmq]# vim nfs-rbac.yaml
---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: nfs-provisioner
  namespace: wiseco
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
   name: nfs-provisioner-runner
   namespace: wiseco
rules:
   -  apiGroups: [""]
      resources: ["persistentvolumes"]
      verbs: ["get", "list", "watch", "create", "delete"]
   -  apiGroups: [""]
      resources: ["persistentvolumeclaims"]
      verbs: ["get", "list", "watch", "update"]
   -  apiGroups: ["storage.k8s.io"]
      resources: ["storageclasses"]
      verbs: ["get", "list", "watch"]
   -  apiGroups: [""]
      resources: ["events"]
      verbs: ["watch", "create", "update", "patch"]
   -  apiGroups: [""]
      resources: ["services", "endpoints"]
      verbs: ["get","create","list", "watch","update"]
   -  apiGroups: ["extensions"]
      resources: ["podsecuritypolicies"]
      resourceNames: ["nfs-provisioner"]
      verbs: ["use"]
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
  name: run-nfs-provisioner
subjects:
  - kind: ServiceAccount
    name: nfs-provisioner
    namespace: wiseco
roleRef:
  kind: ClusterRole
  name: nfs-provisioner-runner
  apiGroup: rbac.authorization.k8s.io

查看並創建

[root@k8s-master01 rabbitmq]# kubectl apply -f nfs-rbac.yaml
serviceaccount/nfs-provisioner created
clusterrole.rbac.authorization.k8s.io/nfs-provisioner-runner created
clusterrolebinding.rbac.authorization.k8s.io/run-nfs-provisioner created

[root@k8s-master01 rabbitmq]# kubectl get sa -n wiseco|grep nfs
nfs-provisioner                1         6h2m

[root@k8s-master01 rabbitmq]# kubectl get clusterrole -n wiseco|grep nfs
nfs-provisioner-runner                                                 2021-02-07T03:30:56Z

[root@k8s-master01 rabbitmq]# kubectl get clusterrolebinding -n wiseco|grep nfs
run-nfs-provisioner                                    ClusterRole/nfs-provisioner-runner                                                 6h2m

  

3)創建RabbitMQ集群的storageclass
[root@k8s-master01 rabbitmq]# ll
total 4
-rw-r--r-- 1 root root 1216 Feb  7 17:33 nfs-rbac.yaml

[root@k8s-master01 rabbitmq]# vim rabbitmq-nfs-class.yaml
apiVersion: storage.k8s.io/v1beta1
kind: StorageClass
metadata:
  name: rabbitmq-nfs-storage
  namespace: wiseco
provisioner: rabbitmq/nfs
reclaimPolicy: Retain

查看並創建

[root@k8s-master01 rabbitmq]# kubectl apply -f rabbitmq-nfs-class.yaml
storageclass.storage.k8s.io/rabbitmq-nfs-storage created

[root@k8s-master01 rabbitmq]# kubectl get sc
NAME                   PROVISIONER    RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
rabbitmq-nfs-storage   rabbitmq/nfs   Retain          Immediate           false                  3s

  

4)創建MongoDB集群的nfs-client-provisioner
[root@k8s-master01 rabbitmq]# ll
total 8
-rw-r--r-- 1 root root 1216 Feb  7 17:33 nfs-rbac.yaml
-rw-r--r-- 1 root root  161 Feb  7 17:37 rabbitmq-nfs-class.yaml

[root@k8s-master01 rabbitmq]# vim rabbitmq-nfs.yml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: rabbitmq-nfs-client-provisioner
  namespace: wiseco
spec:
  replicas: 1
  selector:
    matchLabels:
      app: rabbitmq-nfs-client-provisioner
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: rabbitmq-nfs-client-provisioner
    spec:
      serviceAccount: nfs-provisioner
      containers:
        - name: rabbitmq-nfs-client-provisioner
          image: registry.cn-hangzhou.aliyuncs.com/open-ali/nfs-client-provisioner
          imagePullPolicy: IfNotPresent
          volumeMounts:
            - name: nfs-client-root
              mountPath:  /persistentvolumes
          env:
            - name: PROVISIONER_NAME
              value: rabbitmq/nfs
            - name: NFS_SERVER
              value: 172.16.60.238
            - name: NFS_PATH
              value: /data/storage/k8s/rabbitmq
      volumes:
        - name: nfs-client-root
          nfs:
            server: 172.16.60.238
            path: /data/storage/k8s/rabbitmq

查看並創建

[root@k8s-master01 rabbitmq]# kubectl apply -f rabbitmq-nfs.yml
deployment.apps/rabbitmq-nfs-client-provisioner created

[root@k8s-master01 rabbitmq]# kubectl get pods -n wiseco|grep rabbitmq
rabbitmq-nfs-client-provisioner-c4f95d479-xvm8r   1/1     Running   0          17s

  

4、部署RabbitMQ基於鏡像模式的集群
[root@k8s-master01 rabbitmq]# ll
total 12
-rw-r--r-- 1 root root 1216 Feb  7 17:33 nfs-rbac.yaml
-rw-r--r-- 1 root root  161 Feb  7 17:37 rabbitmq-nfs-class.yaml
-rw-r--r-- 1 root root 1027 Feb  7 17:46 rabbitmq-nfs.yml
[root@k8s-master01 rabbitmq]# mkdir deployment
[root@k8s-master01 rabbitmq]# cd deployment
[root@k8s-master01 deployment]#

  

采用StatefulSet與Headless Service模式部署有狀態的RabbitMQ集群。
rabbitmq.yml文件內容:
[root@k8s-master01 deployment]# vim rabbitmq.yml
---
apiVersion: v1
kind: Service
metadata:
  name: rabbitmq-management
  namespace: wiseco
  labels:
    app: rabbitmq
spec:
  ports:
  - port: 15672
    name: http
  selector:
    app: rabbitmq
  type: NodePort
---
apiVersion: v1
kind: Service
metadata:
  name: rabbitmq
  namespace: wiseco
  labels:
    app: rabbitmq
spec:
  ports:
  - port: 5672
    name: amqp
  - port: 4369
    name: epmd
  - port: 25672
    name: rabbitmq-dist
  clusterIP: None
  selector:
    app: rabbitmq
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
  namespace: wiseco
  name: rabbitmq
spec:
  serviceName: "rabbitmq"
  replicas: 3
  selector:
    matchLabels:
      app: rabbitmq
  template:
    metadata:
      labels:
        app: rabbitmq
    spec:
      affinity:
        podAntiAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            - labelSelector:
                matchExpressions:
                  - key: "app"
                    operator: In
                    values:
                      - rabbitmq
              topologyKey: "kubernetes.io/hostname"
      containers:
      - name: rabbitmq
        image: rabbitmq:3.7-rc-management
        lifecycle:
          postStart:
            exec:
              command:
              - /bin/sh
              - -c
              - >
                if [ -z "$(grep rabbitmq /etc/resolv.conf)" ]; then
                  sed "s/^search \([^ ]\+\)/search rabbitmq.\1 \1/" /etc/resolv.conf > /etc/resolv.conf.new;
                  cat /etc/resolv.conf.new > /etc/resolv.conf;
                  rm /etc/resolv.conf.new;
                fi;
                until rabbitmqctl node_health_check; do sleep 1; done;
                if [ -z "$(rabbitmqctl cluster_status | grep rabbitmq-0)" ]; then
                  touch /gotit
                  rabbitmqctl stop_app;
                  rabbitmqctl reset;
                  rabbitmqctl join_cluster rabbit@rabbitmq-0;
                  rabbitmqctl start_app;
                else
                  touch /notget
                fi;
        env:
        - name: MY_POD_NAME
          valueFrom:
            fieldRef:
              fieldPath: metadata.name
        - name: RABBITMQ_ERLANG_COOKIE
          value: "YZSDHWMFSMKEMBDHSGGZ"
        - name: RABBITMQ_NODENAME
          value: "rabbit@$(MY_POD_NAME)"
        ports:
        - name: http
          protocol: TCP
          containerPort: 15672
        - name: amqp
          protocol: TCP
          containerPort: 5672
        livenessProbe:
          tcpSocket:
            port: amqp
          initialDelaySeconds: 5
          timeoutSeconds: 5
          periodSeconds: 10
        readinessProbe:
          tcpSocket:
            port: amqp
          initialDelaySeconds: 15
          timeoutSeconds: 5
          periodSeconds: 20
        volumeMounts:
        - name: rabbitmq-data
          mountPath: /var/lib/rabbitmq
  volumeClaimTemplates:
  - metadata:
      name: rabbitmq-data
      annotations:
        volume.beta.kubernetes.io/storage-class: "rabbitmq-nfs-storage"
    spec:
      accessModes:
        - ReadWriteMany
      resources:
        requests:
          storage: 10Gi

  

查看並創建

[root@k8s-master01 deployment]# kubectl apply -f rabbitmq.yml
service/rabbitmq-management created
service/rabbitmq created
statefulset.apps/rabbitmq created

[root@k8s-master01 deployment]# kubectl get pods -n wiseco -o wide|grep rabbitmq
rabbitmq-0                                        1/1     Running   0          11m     172.30.85.206    k8s-node01   <none>           <none>
rabbitmq-1                                        1/1     Running   0          9m9s    172.30.217.69    k8s-node04   <none>           <none>
rabbitmq-2                                        1/1     Running   0          7m59s   172.30.135.145   k8s-node03   <none>           <none>
rabbitmq-nfs-client-provisioner-c4f95d479-xvm8r   1/1     Running   0          20h     172.30.217.122   k8s-node04   <none>           <none>

[root@k8s-master01 deployment]# kubectl get svc -n wiseco|grep rabbitmq
rabbitmq              ClusterIP   None             <none>        5672/TCP,4369/TCP,25672/TCP   8m27s
rabbitmq-management   NodePort    10.254.128.136   <none>        15672:32513/TCP               8m27s

  

查看PV、PVC

[root@k8s-master01 deployment]# kubectl get pvc -n wiseco
NAME                       STATUS   VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS           AGE
rabbitmq-data-rabbitmq-0   Bound    pvc-19579da4-fe40-4cc5-abb5-670486cc3f12   10Gi       RWX            rabbitmq-nfs-storage   9m38s
rabbitmq-data-rabbitmq-1   Bound    pvc-13218c20-2a79-40f2-92fa-a18300729c12   10Gi       RWX            rabbitmq-nfs-storage   7m5s
rabbitmq-data-rabbitmq-2   Bound    pvc-7a13561a-1d9c-430c-90df-45ccad455fce   10Gi       RWX            rabbitmq-nfs-storage   5m55s

[root@k8s-master01 deployment]# kubectl get pv
NAME                                       CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS   CLAIM                             STORAGECLASS           REASON   AGE
pvc-13218c20-2a79-40f2-92fa-a18300729c12   10Gi       RWX            Delete           Bound    wiseco/rabbitmq-data-rabbitmq-1   rabbitmq-nfs-storage            7m3s
pvc-19579da4-fe40-4cc5-abb5-670486cc3f12   10Gi       RWX            Delete           Bound    wiseco/rabbitmq-data-rabbitmq-0   rabbitmq-nfs-storage            9m38s
pvc-7a13561a-1d9c-430c-90df-45ccad455fce   10Gi       RWX            Delete           Bound    wiseco/rabbitmq-data-rabbitmq-2   rabbitmq-nfs-storage            5m55s

  

查看NFS共享存儲
NFS服務器(172.16.60.238),查看共享目錄/data/storage/k8s/rabbitmq
[root@k8s-harbor01 ~]# cd /data/storage/k8s/rabbitmq/
[root@k8s-harbor01 rabbitmq]# ll
total 0
drwxrwxrwx 5 polkitd root 70 Feb  8 14:17 wiseco-rabbitmq-data-rabbitmq-0-pvc-19579da4-fe40-4cc5-abb5-670486cc3f12
drwxrwxrwx 5 polkitd root 70 Feb  8 14:19 wiseco-rabbitmq-data-rabbitmq-1-pvc-13218c20-2a79-40f2-92fa-a18300729c12
drwxrwxrwx 5 polkitd root 70 Feb  8 14:21 wiseco-rabbitmq-data-rabbitmq-2-pvc-7a13561a-1d9c-430c-90df-45ccad455fce

[root@k8s-harbor01 rabbitmq]# ls ./*
./wiseco-rabbitmq-data-rabbitmq-0-pvc-19579da4-fe40-4cc5-abb5-670486cc3f12:
config  mnesia  schema

./wiseco-rabbitmq-data-rabbitmq-1-pvc-13218c20-2a79-40f2-92fa-a18300729c12:
config  mnesia  schema

./wiseco-rabbitmq-data-rabbitmq-2-pvc-7a13561a-1d9c-430c-90df-45ccad455fce:
config  mnesia  schema

查看RabbitMQ的三個容器節點的.erlang.cookie,內容是一致的!
[root@k8s-harbor01 rabbitmq]# ll ./*/.erlang.cookie
-rw------- 1 polkitd input 21 Feb  8 14:16 ./wiseco-rabbitmq-data-rabbitmq-0-pvc-19579da4-fe40-4cc5-abb5-670486cc3f12/.erlang.cookie
-rw------- 1 polkitd input 21 Feb  8 14:19 ./wiseco-rabbitmq-data-rabbitmq-1-pvc-13218c20-2a79-40f2-92fa-a18300729c12/.erlang.cookie
-rw------- 1 polkitd input 21 Feb  8 14:20 ./wiseco-rabbitmq-data-rabbitmq-2-pvc-7a13561a-1d9c-430c-90df-45ccad455fce/.erlang.cookie
[root@k8s-harbor01 rabbitmq]# cat ./*/.erlang.cookie
YZSDHWMFSMKEMBDHSGGZ
YZSDHWMFSMKEMBDHSGGZ
YZSDHWMFSMKEMBDHSGGZ

  

5、驗證RabbitMQ集群
進入RabbitMQ集群節點Pod容器,查看RabbitMQ集群狀態(三個Pod查看的集群狀態是一樣的)
登錄rabbitmq-0容器查看集群狀態
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl cluster_status
Cluster status of node rabbit@rabbitmq-0 ...
[{nodes,[{disc,['rabbit@rabbitmq-0','rabbit@rabbitmq-1',
                'rabbit@rabbitmq-2']}]},
 {running_nodes,['rabbit@rabbitmq-2','rabbit@rabbitmq-1','rabbit@rabbitmq-0']},
 {cluster_name,<<"rabbit@rabbitmq-0.rabbitmq.wiseco.svc.cluster.local">>},
 {partitions,[]},
 {alarms,[{'rabbit@rabbitmq-2',[]},
          {'rabbit@rabbitmq-1',[]},
          {'rabbit@rabbitmq-0',[]}]}]


登錄rabbitmq-1容器查看集群狀態
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-1 -n wiseco -- rabbitmqctl cluster_status
Cluster status of node rabbit@rabbitmq-1 ...
[{nodes,[{disc,['rabbit@rabbitmq-0','rabbit@rabbitmq-1',
                'rabbit@rabbitmq-2']}]},
 {running_nodes,['rabbit@rabbitmq-2','rabbit@rabbitmq-0','rabbit@rabbitmq-1']},
 {cluster_name,<<"rabbit@rabbitmq-0.rabbitmq.wiseco.svc.cluster.local">>},
 {partitions,[]},
 {alarms,[{'rabbit@rabbitmq-2',[]},
          {'rabbit@rabbitmq-0',[]},
          {'rabbit@rabbitmq-1',[]}]}]


登錄rabbitmq-2容器查看集群狀態
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-2 -n wiseco -- rabbitmqctl cluster_status
Cluster status of node rabbit@rabbitmq-2 ...
[{nodes,[{disc,['rabbit@rabbitmq-0','rabbit@rabbitmq-1',
                'rabbit@rabbitmq-2']}]},
 {running_nodes,['rabbit@rabbitmq-0','rabbit@rabbitmq-1','rabbit@rabbitmq-2']},
 {cluster_name,<<"rabbit@rabbitmq-0.rabbitmq.wiseco.svc.cluster.local">>},
 {partitions,[]},
 {alarms,[{'rabbit@rabbitmq-0',[]},
          {'rabbit@rabbitmq-1',[]},
          {'rabbit@rabbitmq-2',[]}]}] 
 
 
6、訪問RabbitMQ的Web界面,查看集群狀態
[root@k8s-master01 deployment]# kubectl get svc -n wiseco|grep rabbitmq
rabbitmq              ClusterIP   None             <none>        5672/TCP,4369/TCP,25672/TCP   23m
rabbitmq-management   NodePort    10.254.128.136   <none>        15672:32513/TCP               23m

  

通過K8S的node節點的32513訪問web頁面,用戶名和密碼都是guest

 

7、RabbitMQ的日常操作命令
1)用戶管理
=====================================================================================================
新增一個用戶
# rabbitmqctl add_user Username Password

刪除一個用戶
# rabbitmqctl delete_user Username

修改用戶的密碼
# rabbitmqctl change_password Username Newpassword

查看當前用戶列表
# rabbitmqctl list_users

比如:修改guest用戶密碼、新增或刪除一個用戶
查看當前用戶列表
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl list_users
Listing users ...
user    tags
guest   [administrator]

修改guest用戶密碼為 guest@123
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl change_password guest guest@123
Changing password for user "guest" ..

新增一個用戶,用戶名為kevin,密碼為 kevin@123
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl add_user kevin kevin@123
Adding user "kevin" ...

查看當前用戶列表
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl list_users
Listing users ...
user    tags
guest   [administrator]
kevin   []

設置kevin用戶角色為administrator
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl set_user_tags kevin administrator
Setting tags for user "kevin" to [administrator] ...

查看當前用戶列表
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl list_users
Listing users ...
user    tags
guest   [administrator]
kevin   [administrator]

修改kevin用戶角色為monitoring、policymaker
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl set_user_tags kevin monitoring policymaker
Setting tags for user "kevin" to [monitoring, policymaker] ...

查看當前用戶列表
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl list_users
Listing users ...
user    tags
guest   [administrator]
kevin   [monitoring, policymaker]

刪除kevin用戶
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl delete_user kevin
Deleting user "kevin" ...

查看當前用戶列表
[root@k8s-master01 deployment]# kubectl exec -ti rabbitmq-0 -n wiseco -- rabbitmqctl list_users
Listing users ...
user    tags
guest   [administrator]



2)用戶角色
=====================================================================================================
用戶角色分類
用戶角色可分為五類:超級管理員、監控者、策略制定者、普通管理者以及其他。
超級管理員 (administrator)
可登陸管理控制台(啟用management plugin的情況下),可查看所有的信息,並且可以對用戶,策略(policy)進行操作。
監控者 (monitoring)
可登陸管理控制台(啟用management plugin的情況下),同時可以查看rabbitmq節點的相關信息(進程數,內存使用情況,磁盤使用情況等)
策略制定者 (policymaker)
可登陸管理控制台(啟用management plugin的情況下), 同時可以對policy進行管理。但無法查看節點的相關信息
普通管理者 (management)
僅可登陸管理控制台(啟用management plugin的情況下),無法看到節點信息,也無法對策略進行管理。
其他
無法登陸管理控制台,通常就是普通的生產者和消費者。

相關操作命令:
設置用戶角色的命令為:
# rabbitmqctl set_user_tags User Tag

其中:
User為用戶名
Tag為角色名 (對應於上面的administrator,monitoring,policymaker,management,或其他自定義名稱)。

也可以給同一用戶設置多個角色,例如:
# rabbitmqctl set_user_tags kevin monitoring policymaker



3)用戶權限
=====================================================================================================
用戶權限指的是用戶對exchange,queue的操作權限,包括配置權限,讀寫權限。
配置權限會影響到exchange,queue的聲明和刪除。
讀寫權限影響到從queue里取消息,向exchange發送消息以及queue和exchange的綁定(bind)操作。

例如:
 將queue綁定到某exchange上,需要具有queue的可寫權限,以及exchange的可讀權限;
向exchange發送消息需要具有exchange的可寫權限;
從queue里取數據需要具有queue的可讀權限。

相關操作命令:
設置用戶權限
# rabbitmqctl set_permissions -p VHostPath User ConfP WriteP ReadP

查看(指定hostpath)所有用戶的權限信息
# rabbitmqctl list_permissions [-p VHostPath]

查看指定用戶的權限信息
# rabbitmqctl list_user_permissions User

清除用戶的權限信息
# rabbitmqctl clear_permissions [-p VHostPath] User

設置節點類型
RabbitMQ節點類型分為內存節點和硬盤節點。
如果你想更換節點類型可以通過命令修改:
# rabbitmqctl stop_app
# rabbitmqctl change_cluster_node_type dist
# rabbitmqctl change_cluster_node_type ram
# rabbitmqctl start_app

  

8、模擬RabbitMQ節點故障
模擬故障,重啟其中的一個node節點,比如rabbitmq-0,然后觀察集群狀態:
[root@k8s-master01 deployment]# kubectl get pods -n wiseco -o wide|grep rabbitmq
rabbitmq-0                                        1/1     Running   0          71m   172.30.85.206    k8s-node01   <none>           <none>
rabbitmq-1                                        1/1     Running   0          68m   172.30.217.69    k8s-node04   <none>           <none>
rabbitmq-2                                        1/1     Running   0          67m   172.30.135.145   k8s-node03   <none>           <none>
rabbitmq-nfs-client-provisioner-c4f95d479-xvm8r   1/1     Running   0          21h   172.30.217.122   k8s-node04   <none>           <none>

刪除rabbitmq-0節點
[root@k8s-master01 deployment]# kubectl delete pods rabbitmq-0 -n wiseco
pod "rabbitmq-0" deleted

查看pod,發現rabbitmq-0節點刪除后,重啟需要耗費一段時間
[root@k8s-master01 deployment]# kubectl get pods -n wiseco -o wide|grep rabbitmq
rabbitmq-0                                        0/1     ContainerCreating   0          44s   <none>           k8s-node01   <none>           <none>
rabbitmq-1                                        1/1     Running             0          70m   172.30.217.69    k8s-node04   <none>           <none>
rabbitmq-2                                        1/1     Running             0          69m   172.30.135.145   k8s-node03   <none>           <none>
rabbitmq-nfs-client-provisioner-c4f95d479-xvm8r   1/1     Running             0          21h   172.30.217.122   k8s-node04   <none>           <none>

此時,查看RabbitMQ集群狀態
發現此時,rabbit@rabbitmq-0節點還沒有恢復,running的node節點只有rabbit@rabbitmq-2、rabbit@rabbitmq-1
[root@k8s-master01 ~]# kubectl exec -ti rabbitmq-1 -n wiseco -- rabbitmqctl cluster_status
Cluster status of node rabbit@rabbitmq-1 ...
[{nodes,[{disc,['rabbit@rabbitmq-0','rabbit@rabbitmq-1',
                'rabbit@rabbitmq-2']}]},
 {running_nodes,['rabbit@rabbitmq-2','rabbit@rabbitmq-1']},
 {cluster_name,<<"rabbit@rabbitmq-0.rabbitmq.wiseco.svc.cluster.local">>},
 {partitions,[]},
 {alarms,[{'rabbit@rabbitmq-2',[]},{'rabbit@rabbitmq-1',[]}]}]

  

此時,查看web界面的集群狀態,先后經歷了下面三個狀態:
  • 紅色表示 節點故障。
  • 黃色表示 節點恢復中,暫不可用。
  • 綠色表示 點運行正常。

 

 

 

 

 

9、客戶端訪問RabbitMQ集群地址
客戶端連接RabbitMQ集群地址:rabbitmq-0.rabbitmq.wiseco.svc.cluster.local:5672、rabbitmq-0.rabbitmq.wiseco.svc.cluster.local:5672、rabbitmq-0.rabbitmq.wiseco.svc.cluster.local:5672
連接方式:
  • 客戶端可以連接RabbitMQ集群中的任意一個節點。如果一個節點故障,客戶端自行重新連接到其他的可用節點;
  • 也就是說,RabbitMQ集群有"重連"機制,但是這種集群連接方式對客戶端不透明,不太建議這種連接方式。
推薦方式:給客戶端提供一個統一的透明的集群連接地址
做法:在前面部署LVS或Haproxy,通過四層負載均衡代理后RabbitMQ的三個node節點的5672端口。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM