Rocketmq5.1.3 自主选举\切换 集群k8s部署实践(万字长文)

背景

Rcoketmq官方并没有提供k8s镜像,我使用hub.docker仓库中的镜像,无法在k8s集群中启动成功,此外由于Rocketmq是在代码中写死数据文件保存地址(使用的是$use.home),无法自定义修改,只能通过修改源码调整,并且jvm启动参数xmx,xms无法通过环境变量配置,对低配置环境部署很不友好,因此我最终选择的方案是自己重新做一个镜像,并部署到k8s接集群中。
注意: 阅读本篇内容需要具备docker, k8s, java项目开发构建的基础技能,对于这些技术的细节,本篇不做过多描述。

--------------------- 原创不易,如果大家看完觉得有帮助,希望能多多点赞关注,感谢各位的支持 ----------------------

镜像准备

按照官方推荐,使用JDK1.8,我选择小版本号是1.8u381,系统镜像我用的ubuntu2204,后期好维护
oracle 官网jdk下载地址 : javase8u211-later-archive-downloads
PS:这里有小提示,正常点击下载链接,会让你注册登录,实际不需要,查看下载链接源代码你会发现url这样的

<a class="download-file icn-download-locked" href="https://www.oracle.com/webapps/redirect/signon?nexturl=https://download.oracle.com/otn/java/jdk/8u381-b09/8c876547113c4e4aab3c868e9e0ec572/jdk-8u381-linux-x64.tar.gz" aria-disabled="false">Download jdk-8u381-linux-x64.tar.gz</a>

看到里面的 nexturl=https://xxxxx 了吧,直接复制出来,用这个就可以直接下载了,oracle也够简单粗暴的,不知道啥时候会调整成动态的。。。反正咱也不用收费的,免费的下一次就够了。

docker制作基础镜像过程乏善可陈:

  1. docker run -itd 运行ubuntu的镜像容器(我用的22.04,也可以用其他自己熟悉的系统内核镜像);
  2. 上面安装jdk1.8(这里我用的是),配置环境变量,有许多详细教程,就不赘述了;
  3. 部署安装rocketmq并修改部分源代码及脚本文件,接下来会先详细说明。

下载rocketmq二进制包与源码包

参考 官方下载地址,我个人习惯使用最新版本的前几个版本中,维持时间最长的(说明比较稳定),本次我选择的是5.1.3

在容器中部署二进制包

参考 官方快速开始
过程基本很简单,就是将下载的包解压缩到想要部署的目录中(本次我选择的是/usr/local/rocketmq)即可
可以额外做2个软连接方便以后启动

#启动name server的脚本
ln -s /usr/local/rocketmq/bin/mqnamesrv /usr/bin/mqnamesrv 
#启动broker server的脚本
ln -s /usr/local/rocketmq/bin/mqbroker /usr/bin/mqbroker 

这里我们可以使用同一个镜像来部署name-server 与 broker-server,它们运行环境是一样的,只是启动服务命令不同

修改源代码使用新的环境变量来配置日志目录位置

用idea加载源代码项目,查找"$user.home",修改找出来的文件(.log-backj.xml 与 .java),之所以没有采用直接配置user.home的环境变量到其他目录,是怕有引发其他问题,user.home代表用户目录,如果把这个环境变量名替换成其他的,我用的是RMQ_HOME,可能会引发其他服务出现问题。

替换范围(可以忽略test子模块的文件):
xml
在这里插入图片描述

java
在这里插入图片描述

然后通过maven重新构建整个工程(需要使用jdk1.8),即构建项目根目录(rocketmq-all)下的pom.xml,lifecycle选择 package就行,把skip-test点一下。
然后再各子模块的工程tartget目录中找到构建出的新文件

也可以通过官方命令行使用:
mvn -Prelease-all -DskipTests -Dspotbugs.skip=true clean install -U
然后去 distribution/target/rocketmq-5.1.4/rocketmq-5.1.4中找文件

需要替换的文件我列出来以免遗漏
jar文件:
rocketmq-acl-5.1.3.jar
rocketmq-client-5.1.3.jar
rocketmq-store-5.1.3.jar
rocketmq-broker-5.1.3.jar
rocketmq-common-5.1.3.jar
rocketmq-tiered-store-5.1.3.jar

log-back.xml文件
rmq.broker.logback.xml
rmq.client.logback.xml
rmq.controller.logback.xml
rmq.namesrv.logback.xml
rmq.proxy.logback.xml
rmq.tools.logback.xml

日志文件这里还有一个地方可以修改(不必须),里面默认固定输出info的信息,部署后输出信息会很多,日志占用空间大。
这里也可以改成变量,比如把rmq.tools.logback.xml 中 level=“INFO” 替换为 level=“${TOOLS_LOG_LEVEL}” ,其他文件也类似
,这样以后也可以通过给容器挂载不同的环境变量的值来控制日志输出级别。

使用dcoker cp 命令,将以上这些文件替换到docker容器的rocketmq部署目录中,以我的为例,部署目录 /usr/local/rocketmq
jar文件就替换到 /usr/local/rocketmq/lib
xml文件就替换到 /usr/local/rocketmq/conf

修改sh脚本文件
以上我们增加了环境变量的支持,还需要在服务启动脚本中对环境变量做检查自动创建目录,在没有配置环境变量时给定默认值,以免没有配置环境变量时服务启动失败。
涉及脚本文件:
runserver.sh , runbroker.sh
都在rocketmq部署目录/bin下 ,需要修改的内容基本是一样的,先说runserver.sh

首先找到

DIR_SIZE_IN_MB=600

在其下方添加

if [ "$BROKER_LOG_LEVEL" = "" ]; then
   export BROKER_LOG_LEVEL="INFO"
fi

if [ "$CONTROLLER_LOG_LEVEL" = "" ]; then
    export CONTROLLER_LOG_LEVEL="INFO"
fi

if [ "$NAMESRV_LOG_LEVEL" = "" ]; then
    export NAMESRV_LOG_LEVEL="INFO"
fi

if [ "$PROXY_LOG_LEVEL" = "" ]; then
   export PROXY_LOG_LEVEL="INFO"
fi

if [ "$TOOLS_LOG_LEVEL" = "" ]; then
    export TOOLS_LOG_LEVEL="INFO"
fi


if [ "$JVM_OPT_XMX" = "" ]; then
   export JVM_OPT_XMX="4g"
fi
if [ "$JVM_OPT_XMS" = "" ]; then
    export JVM_OPT_XMS="4g"
fi

if [ "$JVM_OPT_XMN" = "" ]; then
    export JVM_OPT_XMN="2g"
fi

if [ "$RMQ_HOME" = "" ]; then
    export RMQ_HOME=$user.home
elif [ ! -d "$RMQ_HOME" ]; then
       mkdir -p $RMQ_HOME
fi
  • 这里的$xxxx_LOG_LEVEL 就是我之前在log-back.xml中定义的各日志输出级别的变量名,跟你自己配置保持一致就行,没配置不用管,直接加上也没事
  • "JVM_OPT_XMX,JVM_OPT_XMS,JVM_OPT_XMN 为启动服务时内存堆的配置需要,在替换到启动命令中,下面会说
  • RMQ_HOME 就是我们之前做了替换的环境变量,这里也修改成跟你一样的,如果没配置,默认跟原来一样使用$user.home的值

然后找到

choose_gc_log_directory()

将方法整体替换为

choose_gc_log_directory()
{
    if [ -d "$RMQ_HOME" ]; then
            mkdir ${RMQ_HOME}"/gclog"
            GC_LOG_DIR="$RMQ_HOME/gclog"
        else
                case "`uname`" in
                        Darwin)
                                if [ ! -d "/Volumes/RAMDisk" ]; then
                                        # create ram disk on Darwin systems as gc-log directory
                                        DEV=`hdiutil attach -nomount ram://$((2 * 1024 * DIR_SIZE_IN_MB))` > /dev/null
                                        diskutil eraseVolume HFS+ RAMDisk ${DEV} > /dev/null
                                        echo "Create RAMDisk /Volumes/RAMDisk for gc logging on Darwin OS."
                                fi
                                GC_LOG_DIR="/Volumes/RAMDisk/gclog"
                        ;;
                        *)
                                # check if /dev/shm exists on other systems


                                if [ -d "/dev/shm" ]; then

                                        if [ ! -d "/dev/shm/gclog" ]; then
                                                mkdir /dev/shm/gclog
                                        fi
                                        GC_LOG_DIR="/dev/shm/gclog"
                                else
                                        GC_LOG_DIR=${BASE_DIR}"/gclog"
                                fi
                        ;;
                esac
        fi
}
这里是为了也将gclog输出到我们指定的目录中

最后是找

choose_gc_options()

将里面Xms Xmx Xmn的设置由原来的固定值改为变量

-Xms$JVM_OPT_XMS -Xmx$JVM_OPT_XMX -Xmn$JVM_OPT_XMN
-Xms$JVM_OPT_XMS -Xm$JVM_OPT_XMX

runbroker.sh的修改过程是一样,稍有不同的是替换Xms Xmx Xmn命令的位置有些变化

JAVA_OPT="${JAVA_OPT} -Xmn$JVM_OPT_XMN 
JAVA_OPT="${JAVA_OPT} -server -Xms$JVM_OPT_XMS -Xmx$JVM_OPT_XMX"

修改后
先尝试用 mqnamesrv & 启动namerserver 服务看看是否正常 (应该是一次启动成功的)
验证namesrv是否启动成功
$ tail -f ${RMQ_HOME}/logs/rocketmqlogs/namesrv.log
The Name Server boot success…

再此基础之上用 mqbroker -n localhost:9876 --enable-proxy & 启动borker
验证broker是否启动成功, 比如, broker的ip是192.168.1.2 然后名字是broker-a
$ tail -f ${RMQ_HOME}/logs/rocketmqlogs/proxy.log
The broker[broker-a,192.169.1.2:10911] boot success…

这里要注意,如果不配置xmx xms xmn mameserver启动默认是 Xmx=4g Xms=4g Xmn=2g,broker默认是 Xmx=8g Xms=8g xmn=4g,确保你的运行环境足够,我测试的结果使用 xmx=2g xms=2g xmn=1g,是可以正常启动的(同时启动nameserver 与 broker),再小点也可以启动,不过用起来会出问题。
至此镜像制作完毕,先试用docker commit 将容器导出为本地镜像,在通过docker push 上传到自己私服上,没有搭建私服用hub.docker(访问受限)或者 aliyun提供的个人私服(不允许商用)也可以。

至于私服如何搭建,使用这里就不赘述了,我之前写过k8s部署私服的文章 轻量级开源 docker私服管理工具部署实践 ,或者参考其他文章搭建也可,网上有很多。

我这里最终上传到私服的镜像tag为 registry:80/middleware/rocketmq5.1.3 后文部署k8s容器都是用这个镜像地址。

部署k8s

  • 需要准备2个部署文件
    1.nameserver
    2.broker
    由于都是有状态的应用,所以要使用StatefulSet容器,这按照最小集群
    1 nameserver ---- 2 brokerserver【 1 master 1 slave 】
    使用rocketmq5.x发布的 基于controler 自主选举切换的集群,无需手动配置broker主从
    官方文档:主备自动切换模式部署

  • 样例中我使用的是本地存储模式,基于local-path-provisioner,通过storeclass 声明pvc 动态创建 pv
    这个网上也有部署说明,很简单,大家可以自己k8s集群的情况进行存储卷Volume配置

  • nameserver与brokerserver的配置文件,acl访问控制配置文件,我都用configmap抽出来了,方便后期维护

  • namserver加了一个service负载,以便于broker可以通过域名访问到nameserver,后续增加nameserver的容器数量按照官方配置是需要对应增加新的service,然后在添加到broker的配置中,不能通过一个service负载地址来代理(其实我觉得这么做也可以,只是还没有时间验证,有兴趣的同学可以自己试一下)

  • 为了便于以后管理,所有service采用静态的cluster ip,需要自行管理ip使用,以免冲突

下面上这2个核心的yaml文件,比较长,相关配置我都尽量增加了说明

k8s部署文件

  • namespace:mq 是我与现在k8s集群中创建的

  • rocketmq-nsrv-01 代表只是01号集群,以适应多集群的部署,同样01集群的broker组也会命名为rocketmq-broker-01
    集群中的第1个容器的name 为xxxx-010 ,第2个容器为011 ,对应的configmap资源也如此命名

  • 同1个集群中的容器共享一个pvc存储空间如:rocketmq-nsrv-01-pvc,通过给容器注入$POD_NAME变量,并加入到存储卷映射路径中以区分开。

nameserver

---

#声明存储使用
#local存储  storage_class:local-path-provisioner(rancher)
apiVersion: v1 
kind: PersistentVolumeClaim
metadata:
  name: rocketmq-nsrv-01-pvc
  namespace:  mq
spec:
  accessModes:
    - ReadWriteOnce #本地存储只支持ReadWriteOnce
  storageClassName: local-path #local-path: 容器删除,存储local-path动态删除,local-path-retain: 容器删除,存储local-path保留,local-path|local-path-retain为手动安装的storageclass
  resources:
    requests:
      storage: 5Gi #声明最少要使用存储空间,不足则无法创建 Gi=G Mi=M 
  #persistentVolumeReclaimPolicy: Delete # PVC 回收策略 Retain 保留| Delete 清除 | PV: local-path-provisioner(rancher) 不支持设置该属性
  
---

# mysql service

apiVersion: v1
kind: Service
metadata:
  name: rocketmq-nsrv-01-svc
  namespace:  mq
  annotations: 
    desc : rocketmq 01 集群 name-server的服务访问入口
spec:
  selector:
    k8s-app: rocketmq-nsrv-01
  type: ClusterIP   #type:  ClusterIP【默认】 | NodePort | LoadBalancer(外部负载均衡) | ExternalName (外部DNS解析)
  clusterIP: 10.106.210.1
  ports:
    - port: 9876
      targetPort: 9876
      name: nsrv-port
    - port: 9877
      targetPort: 9877
      name: controller-port
      #nodePort: 32000
      
---

apiVersion: apps/v1
kind: StatefulSet # Deployment | StatefulSet | DaemonSet | JobSet
metadata: 
  name:  rocketmq-nsrv-01
  namespace:  mq
spec: 
  replicas: 1  #运行副本数
  selector: 
    matchLabels: 
      k8s-app:  rocketmq-nsrv-01 #与下方template节点中的 labels 保持一致
  revisionHistoryLimit: 10 #设定保留最近的几个revision 用于回滚,默认10
  #serviceName: "nginx-headless" #设置绑定的service,以支持内部dns访问 <pod-name>.<svc-name>.<namespace>.svc.cluster.local
  updateStrategy: #更新策略 [Statefulset]
  #strategy: #更新策略 [Deployment]
    type: RollingUpdate # RollingUpdate (滚动更新) | OnDelete (删除时更新)
    rollingUpdate:
      #maxSurge: 1  #[Deployment]支持-升级过程中可以启动超过原先设置的POD数量的上限:数量 或 百分比 1 | 20%
      #maxUnavailable: 1 #[Deployment]支持-升级过程中无法提供服务的POD数量的上限:数量 或 百分比 1 | 20%,最好与maxSurge保持一致,这样能确保更新过程中的服务能力不会下降
      partition: 0 #[Statefulset] 灰度发布控制器,每次只更新部署的pod序号 >= partition的pod,如果有5个pod[0-4],0=更新所有,4=更新1pod,3=更新2pod
  template: 
    metadata: 
      labels: 
         k8s-app: rocketmq-nsrv-01
    spec: 
      #imagePullSecrets:                        #私服认证信息
      #- name: jenkins-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      restartPolicy: Always 
      terminationGracePeriodSeconds: 30 #容器被删除变为Terminating状态的等待时间,默认是30s,以便于做一些容器删除前的处理工作
      imagePullSecrets:                        #私服认证信息
      - name: local-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      #initContainers:
      #- name: init-deploy
      #  image: 8.0.36
      #  command: 
      #  - "sh" 
      #  - "-c"
      #  - >  # 初始化用于部署的文件资源
      #    cd /data/deploy;
      #  volumeMounts:
      #  - name: api-admin-volume  #挂载部署目录
      #    mountPath: /data/deploy
      #    subPath: deploy
      containers:  
        - name: rocketmq-nsrv-010
          image: registry:80/middleware/rocketmq5.1.3:1.0
          imagePullPolicy: IfNotPresent # IfNotPresent | Always | Never
          resources:
            requests:
              memory: "2500Mi" #Gi=G Mi=M 只支持整数
              #cpu: "1000m" #1000m=1cpu (cpu物理线程)
            limits:
              memory: "2500Mi" #Gi=G Mi=M 只支持整数
              cpu: "1000m"  #1000m=1cpu (cpu物理线程)
          #securityContext: ###添加参数启用容器root权限
          #  privileged: true
          ports: 
          - containerPort: 9876
            protocol: TCP
          #startupProbe: #容器启动探针,失败自动重启 结果Success:表示通过检测| Failure:表示未通过检测|Unknown:表示检测没有正常进行。 
          #  tcpSocket:
          #    port: 9876
          #  initialDelaySeconds: 10 #容器启动后要等待多少秒后就探针开始工作,单位“秒”,默认是 0 秒,最小值是 0
            #periodSeconds: 10 #执行探测的时间间隔(单位是秒),默认为 10s,单位“秒”,最小值是 1
            #timeoutSeconds: 2 #探针执行检测请求后,等待响应的超时时间,默认为 1s,单位“秒”,最小值是 1
            #successThreshold: 1 #探针检测失败后认为成功的最小连接成功次数,默认为 1s,在 Liveness 探针中必须为 1,最小值为 1。
            #failureThreshold: 3 #探测失败的重试次数,重试一定次数后将认为失败,在 readiness 探针中,Pod会被标记为未就绪,默认为 3,最小值为 1
          #lifecycle:
          #  postStart:  #通过postStart 钩子函数做初始化|如果失败会重启容器
          #    exec: 
          #      command: # 设置/etc/nginx/nginx.conf - /data/nginx/nginx.conf的软连接
          #        - "sh" 
          #        - "-c"
          #        - >  # 设置registry垃圾回收器的定时任务,清理日志的定时任务并启动调度服务
          #          rm -f /etc/nginx/nginx.conf;
          #          ln -s /data/nginx/nginx.conf /etc/nginx/nginx.conf;
          #          nginx -s reload 
          command: ["/bin/sh","-c"] #添加registry垃圾回收定时任务,并启动系统定时调度服务
          args: #可以设置多行命令,不过启动后初始化还是推荐使用postStart钩子函数来执行,不能有#注释符
          #mqnamesrv -c /data/conf/namesrv.conf
          - | 
            mqnamesrv -c /data/conf/namesrv.conf
 
          env:   #环境变量配置
          - name: "JVM_OPT_XMX"  #设置jvm opt xmx
            value: "2g"
          - name: "JVM_OPT_XMS"  #设置jvm opt xms
            value: "2g"
          - name: "JVM_OPT_XMN"  #设置jvm opt xmn
            value: "1g"
          - name: "RMQ_HOME"  #设置jvm opt xmn
            value: "/data"
          - name: "BROKER_LOG_LEVEL"  #设置BROKER_LOG_LEVEL
            value: "WARN"
          - name: "CONTROLLER_LOG_LEVEL"  #设置CONTROLLER_LOG_LEVEL
            value: "WARN"
          - name: "NAMESRV_LOG_LEVEL"  #设置NAMESRV_LOG_LEVEL
            value: "WARN"
          - name: "TOOLS_LOG_LEVEL"  #设置TOOLS_LOG_LEVEL
            value: "WARN"
          - name: "PROXY_LOG_LEVEL"  #设置PROXY_LOG_LEVEL
            value: "WARN"
          - name: POD_NAME
            valueFrom: 
              fieldRef: 
                apiVersion: v1
                fieldPath: metadata.name
          volumeMounts: 
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data
            subPathExpr: $(POD_NAME)/data
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data/logs
            subPathExpr: $(POD_NAME)/log
          - name: rockmq-nsrv-010-config  #挂载配置文件
            mountPath: /data/conf
          - name: host-time  #挂载本地时区
            mountPath: /etc/localtime
            readOnly: true
      volumes: 
      - name: rocketmq-volume  #使用pvc
        persistentVolumeClaim:
          claimName:  rocketmq-nsrv-01-pvc
      - name: rockmq-nsrv-010-config  #使用pvc
        configMap:    #使用configMap
          name:  rockmq-nsrv-010-config
          items: 
          - key: namesrv.conf
            path: namesrv.conf
      - name: host-time
        hostPath: #挂载本地时区
          path: /etc/localtime
          type: ""

---

apiVersion: v1
kind: ConfigMap #配置信息
metadata:
  name: rockmq-nsrv-010-config
  namespace:  mq
data:
  namesrv.conf: |
    #启用 Controller 自动主从切换模式
    enableControllerInNamesrv = true
    #DLedger Raft Group 的名字,同一个 DLedger Raft Group 保持一致即可,同组节点组成1个raft集群,允许单点
    controllerDLegerGroup = group1
    #内各节点的端口信息,格式:{DLegerSelfId}-{ip}{端口} 同一个 Group 内的各个节点配置必须要保证一致。
    controllerDLegerPeers = n10-rocketmq-nsrv-01-svc:9877
    #当前节点的DLegerSelfId 必须属于 controllerDLegerPeers 中的一个;同 Group 内各个节点要唯一。
    controllerDLegerSelfId = n10
    #controller 日志存储位置。controller 是有状态的,controller 重启或宕机需要依靠日志来恢复数据,该目录非常重要,不可以轻易删除。
    controllerStorePath = /data/DledgerController
    #是否可以从 SyncStateSet 以外选举 Master,若为 true,可能会选取数据落后的副本作为 Master 而丢失消息,默认为 false。
    enableElectUncleanMaster = false
    #当 Broker 副本组上角色发生变化时是否主动通知,默认为 true
    notifyBrokerRoleChanged = true
    
---

brokerserver

  • 同一组broker的主从节点,其brokername要保持相同,由于采用的是基于controller自主选举的模式,不需要配置
    brokerId , brokerRole,此模式下,broker主节点挂掉或者重启,从节点会自动选举为新的主节点
  • 由于namerver 与 brokerserver都是用状态的,都会各自保存节点信息与状态的元数据,这意味着2边必须一致,集群才能正常运转,也就是说各节点可以重启,可以新增节点,可以删除broker节点,但如果只有1个nameserver节点,且该节点删除重建,则对应broker节点也需要删除重建,无法在现有数据状态下,直接使用新的nameserver节点(master无法选举成功),
    就算修改namerserver enableElectUncleanMaster = true 让新节点可以参与选主(官方不推荐,可能会造成数据丢失),也不行,我本人没有尝试成功。
    kubectl delete -f 要慎重 !!!
---

#声明存储使用
#local存储  storage_class:local-path-provisioner(rancher)
apiVersion: v1 
kind: PersistentVolumeClaim
metadata:
  name: rocketmq-broker-01-pvc
  namespace:   mq
spec:
  accessModes:
    - ReadWriteOnce #本地存储只支持ReadWriteOnce
  storageClassName: local-path #local-path: 容器删除,存储local-path动态删除,local-path-retain: 容器删除,存储local-path保留,local-path|local-path-retain为手动安装的storageclass
  resources:
    requests:
      storage: 20Gi #声明最少要使用存储空间,不足则无法创建 Gi=G Mi=M 
  #persistentVolumeReclaimPolicy: Delete # PVC 回收策略 Retain 保留| Delete 清除 | PV: local-path-provisioner(rancher) 不支持设置该属性
  
---

## mysql service
#
#apiVersion: v1
#kind: Service
#metadata:
#  name: rocketmq-broker-010-svc
#  namespace:    mq
#  annotations: 
#    desc : rocketmq 01集群 broker:rocketmq-broker-010 的负载访问入口
#spec:
#  selector:
#    k8s-app: rocketmq-broker-01
#  type: ClusterIP   #type:  ClusterIP【默认】 | NodePort | LoadBalancer(外部负载均衡) | ExternalName (外部DNS解析)
#  clusterIP: 10.106.211.1
#  ports:
#    - port: 10911
#      targetPort: 10911
#      name: broker-port
#    - port: 8081
#      targetPort: 8081
#      name: proxy-port
#      #nodePort: 32000
#      
#---

apiVersion: apps/v1
kind: StatefulSet # Deployment | StatefulSet | DaemonSet | JobSet
metadata: 
  name:  rocketmq-broker-010
  namespace:   mq
spec: 
  replicas: 1  #运行副本数
  selector: 
    matchLabels: 
      k8s-app:  rocketmq-broker-01 #与下方template节点中的 labels 保持一致
  revisionHistoryLimit: 10 #设定保留最近的几个revision 用于回滚,默认10
  #serviceName: "nginx-headless" #设置绑定的service,以支持内部dns访问 <pod-name>.<svc-name>.<namespace>.svc.cluster.local
  updateStrategy: #更新策略 [Statefulset]
  #strategy: #更新策略 [Deployment]
    type: RollingUpdate # RollingUpdate (滚动更新) | OnDelete (删除时更新)
    rollingUpdate:
      #maxSurge: 1  #[Deployment]支持-升级过程中可以启动超过原先设置的POD数量的上限:数量 或 百分比 1 | 20%
      #maxUnavailable: 1 #[Deployment]支持-升级过程中无法提供服务的POD数量的上限:数量 或 百分比 1 | 20%,最好与maxSurge保持一致,这样能确保更新过程中的服务能力不会下降
      partition: 0 #[Statefulset] 灰度发布控制器,每次只更新部署的pod序号 >= partition的pod,如果有5个pod[0-4],0=更新所有,4=更新1pod,3=更新2pod
  template: 
    metadata: 
      labels: 
         k8s-app: rocketmq-broker-01
    spec: 
      #imagePullSecrets:                        #私服认证信息
      #- name: jenkins-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      restartPolicy: Always 
      affinity: 
        nodeAffinity: # node 亲和度
          requiredDuringSchedulingIgnoredDuringExecution: #硬亲和
            nodeSelectorTerms: 
            - matchExpressions:  
              - key: podtype 
                operator: NotIn
                values: 
                - web
                - manager
          preferredDuringSchedulingIgnoredDuringExecution:
          - weight: 100		#软亲和匹配条件1,权重100优先级
            preference: 
              matchExpressions: 
              - key: podtype  
                operator: In
                values: 
                - io
      terminationGracePeriodSeconds: 30 #容器被删除变为Terminating状态的等待时间,默认是30s,以便于做一些容器删除前的处理工作
      imagePullSecrets:                        #私服认证信息
      - name: local-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      #initContainers:
      #- name: init-deploy
      #  image: 8.0.36
      #  command: 
      #  - "sh" 
      #  - "-c"
      #  - >  # 初始化用于部署的文件资源
      #    cd /data/deploy;
      #  volumeMounts:
      #  - name: api-admin-volume  #挂载部署目录
      #    mountPath: /data/deploy
      #    subPath: deploy
      containers:  
        - name: rocketmq-broker-010
          image: registry:80/middleware/rocketmq5.1.3:1.0
          imagePullPolicy: IfNotPresent # IfNotPresent | Always | Never
          resources:
            requests:
              memory: "3Gi" #Gi=G Mi=M 只支持整数
              #cpu: "1000m" #1000m=1cpu (cpu物理线程)
            limits:
              memory: "3Gi" #Gi=G Mi=M 只支持整数
              cpu: "2000m"  #1000m=1cpu (cpu物理线程)
          #securityContext: ###添加参数启用容器root权限
          #  privileged: true
          ports: 
          - containerPort: 10911
            protocol: TCP
          #startupProbe: #容器启动探针,失败自动重启 结果Success:表示通过检测| Failure:表示未通过检测|Unknown:表示检测没有正常进行。 
          #  tcpSocket:
          #    port: 9876
          #  initialDelaySeconds: 10 #容器启动后要等待多少秒后就探针开始工作,单位“秒”,默认是 0 秒,最小值是 0
            #periodSeconds: 10 #执行探测的时间间隔(单位是秒),默认为 10s,单位“秒”,最小值是 1
            #timeoutSeconds: 2 #探针执行检测请求后,等待响应的超时时间,默认为 1s,单位“秒”,最小值是 1
            #successThreshold: 1 #探针检测失败后认为成功的最小连接成功次数,默认为 1s,在 Liveness 探针中必须为 1,最小值为 1。
            #failureThreshold: 3 #探测失败的重试次数,重试一定次数后将认为失败,在 readiness 探针中,Pod会被标记为未就绪,默认为 3,最小值为 1
          #lifecycle:
          #  postStart:  #通过postStart 钩子函数做初始化|如果失败会重启容器
          #    exec: 
          #      command: # 设置/etc/nginx/nginx.conf - /data/nginx/nginx.conf的软连接
          #        - "sh" 
          #        - "-c"
          #        - >  # 设置registry垃圾回收器的定时任务,清理日志的定时任务并启动调度服务
          #          rm -f /etc/nginx/nginx.conf;
          #          ln -s /data/nginx/nginx.conf /etc/nginx/nginx.conf;
          #          nginx -s reload 
          command: ["/bin/sh","-c"] #添加registry垃圾回收定时任务,并启动系统定时调度服务
          args: #可以设置多行命令,不过启动后初始化还是推荐使用postStart钩子函数来执行,不能有#注释符
          #ln -s /data/conf/acl/acl.yml /usr/local/rocketmq/conf/acl.yml;
          - | 
            if [ ! -d "/usr/local/rocketmq/conf/acl" ]; then 
                mkdir -p /usr/local/rocketmq/conf/acl
            fi
            ln -s /data/conf/acl/plain_acl.yml /usr/local/rocketmq/conf/acl/plain_acl.yml;
            mqbroker -c /data/conf/broker.conf -n rocketmq-nsrv-01-svc:9876 --enable-proxy 
          env:   #环境变量配置
          - name: "JVM_OPT_XMX"  #设置jvm opt xmx
            value: "2g"
          - name: "JVM_OPT_XMS"  #设置jvm opt xms
            value: "2g"
          - name: "JVM_OPT_XMN"  #设置jvm opt xmn
            value: "1g"
          - name: "BROKER_LOG_LEVEL"  #设置BROKER_LOG_LEVEL
            value: "INFO"
          - name: "CONTROLLER_LOG_LEVEL"  #设置CONTROLLER_LOG_LEVEL
            value: "WARN"
          - name: "NAMESRV_LOG_LEVEL"  #设置NAMESRV_LOG_LEVEL
            value: "WARN"
          - name: "TOOLS_LOG_LEVEL"  #设置TOOLS_LOG_LEVEL
            value: "WARN"
          - name: "PROXY_LOG_LEVEL"  #设置PROXY_LOG_LEVEL
            value: "WARN"
          - name: "RMQ_HOME"  #设置jvm opt xmn
            value: "/data"
          - name: POD_NAME
            valueFrom: 
              fieldRef: 
                apiVersion: v1
                fieldPath: metadata.name
          volumeMounts: 
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data
            #subPath: data
            subPathExpr: $(POD_NAME)/data
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data/logs
            subPathExpr: $(POD_NAME)/log
          - name: rockmq-broker-010-config  #挂载配置文件 
            mountPath: /data/conf
          - name: rockmq-broker-acl-config  #挂载配置文件 
            mountPath: /data/conf/acl
          - name: host-time  #挂载本地时区
            mountPath: /etc/localtime
            readOnly: true
            
      volumes: 
      - name: rocketmq-volume  #使用pvc
        persistentVolumeClaim:
          claimName:  rocketmq-broker-01-pvc
      - name: host-time
        hostPath: #挂载本地时区
          path: /etc/localtime
          type: ""
      - name: rockmq-broker-010-config  #使用configMap
        configMap:    
          name: rockmq-broker-010-config
          items: 
          - key: broker.conf
            path: broker.conf
      - name: rockmq-broker-acl-config  #使用configMap
        configMap:    
          name: rockmq-broker-acl-config
          items: 
          - key: plain_acl.yml
            path: plain_acl.yml



---

apiVersion: apps/v1
kind: StatefulSet # Deployment | StatefulSet | DaemonSet | JobSet
metadata: 
  name:  rocketmq-broker-011
  namespace:   mq
spec: 
  replicas: 1  #运行副本数
  selector: 
    matchLabels: 
      k8s-app:  rocketmq-broker-01 #与下方template节点中的 labels 保持一致
  revisionHistoryLimit: 10 #设定保留最近的几个revision 用于回滚,默认10
  #serviceName: "nginx-headless" #设置绑定的service,以支持内部dns访问 <pod-name>.<svc-name>.<namespace>.svc.cluster.local
  updateStrategy: #更新策略 [Statefulset]
  #strategy: #更新策略 [Deployment]
    type: RollingUpdate # RollingUpdate (滚动更新) | OnDelete (删除时更新)
    rollingUpdate:
      #maxSurge: 1  #[Deployment]支持-升级过程中可以启动超过原先设置的POD数量的上限:数量 或 百分比 1 | 20%
      #maxUnavailable: 1 #[Deployment]支持-升级过程中无法提供服务的POD数量的上限:数量 或 百分比 1 | 20%,最好与maxSurge保持一致,这样能确保更新过程中的服务能力不会下降
      partition: 0 #[Statefulset] 灰度发布控制器,每次只更新部署的pod序号 >= partition的pod,如果有5个pod[0-4],0=更新所有,4=更新1pod,3=更新2pod
  template: 
    metadata: 
      labels: 
         k8s-app: rocketmq-broker-01
    spec: 
      #imagePullSecrets:                        #私服认证信息
      #- name: jenkins-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      restartPolicy: Always 
      terminationGracePeriodSeconds: 30 #容器被删除变为Terminating状态的等待时间,默认是30s,以便于做一些容器删除前的处理工作
      imagePullSecrets:                        #私服认证信息
      - name: local-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      #initContainers:
      #- name: init-deploy
      #  image: 8.0.36
      #  command: 
      #  - "sh" 
      #  - "-c"
      #  - >  # 初始化用于部署的文件资源
      #    cd /data/deploy;
      #  volumeMounts:
      #  - name: api-admin-volume  #挂载部署目录
      #    mountPath: /data/deploy
      #    subPath: deploy
      containers:  
        - name: rocketmq-broker-011
          image: registry:80/middleware/rocketmq5.1.3:1.0
          imagePullPolicy: IfNotPresent # IfNotPresent | Always | Never
          resources:
            requests:
              memory: "2500Mi" #Gi=G Mi=M 只支持整数
              #cpu: "1000m" #1000m=1cpu (cpu物理线程)
            limits:
              memory: "2500Mi" #Gi=G Mi=M 只支持整数
              cpu: "2000m"  #1000m=1cpu (cpu物理线程)
          #securityContext: ###添加参数启用容器root权限
          #  privileged: true
          ports: 
          - containerPort: 10911
            protocol: TCP
          #startupProbe: #容器启动探针,失败自动重启 结果Success:表示通过检测| Failure:表示未通过检测|Unknown:表示检测没有正常进行。 
          #  tcpSocket:
          #    port: 9876
          #  initialDelaySeconds: 10 #容器启动后要等待多少秒后就探针开始工作,单位“秒”,默认是 0 秒,最小值是 0
            #periodSeconds: 10 #执行探测的时间间隔(单位是秒),默认为 10s,单位“秒”,最小值是 1
            #timeoutSeconds: 2 #探针执行检测请求后,等待响应的超时时间,默认为 1s,单位“秒”,最小值是 1
            #successThreshold: 1 #探针检测失败后认为成功的最小连接成功次数,默认为 1s,在 Liveness 探针中必须为 1,最小值为 1。
            #failureThreshold: 3 #探测失败的重试次数,重试一定次数后将认为失败,在 readiness 探针中,Pod会被标记为未就绪,默认为 3,最小值为 1
          #lifecycle:
          #  postStart:  #通过postStart 钩子函数做初始化|如果失败会重启容器
          #    exec: 
          #      command: # 设置/etc/nginx/nginx.conf - /data/nginx/nginx.conf的软连接
          #        - "sh" 
          #        - "-c"
          #        - >  # 设置registry垃圾回收器的定时任务,清理日志的定时任务并启动调度服务
          #          rm -f /etc/nginx/nginx.conf;
          #          ln -s /data/nginx/nginx.conf /etc/nginx/nginx.conf;
          #          nginx -s reload 
          command: ["/bin/sh","-c"] #添加registry垃圾回收定时任务,并启动系统定时调度服务
          args: #可以设置多行命令,不过启动后初始化还是推荐使用postStart钩子函数来执行,不能有#注释符
          #ln -s /data/conf/acl/acl.yml /usr/local/rocketmq/conf/acl.yml;
          - | 
            if [ ! -d "/usr/local/rocketmq/conf/acl" ]; then 
                mkdir -p /usr/local/rocketmq/conf/acl
            fi
            ln -s /data/conf/acl/plain_acl.yml /usr/local/rocketmq/conf/acl/plain_acl.yml;
            mqbroker -c /data/conf/broker.conf -n rocketmq-nsrv-01-svc:9876 --enable-proxy 
          env:   #环境变量配置
          - name: "JVM_OPT_XMX"  #设置jvm opt xmx
            value: "2g"
          - name: "JVM_OPT_XMS"  #设置jvm opt xms
            value: "2g"
          - name: "JVM_OPT_XMN"  #设置jvm opt xmn
            value: "1g"
          - name: "RMQ_HOME"  #设置jvm opt xmn
            value: "/data"
          - name: "BROKER_LOG_LEVEL"  #设置BROKER_LOG_LEVEL
            value: "INFO"
          - name: "CONTROLLER_LOG_LEVEL"  #设置CONTROLLER_LOG_LEVEL
            value: "WARN"
          - name: "NAMESRV_LOG_LEVEL"  #设置NAMESRV_LOG_LEVEL
            value: "WARN"
          - name: "TOOLS_LOG_LEVEL"  #设置TOOLS_LOG_LEVEL
            value: "WARN"
          - name: "PROXY_LOG_LEVEL"  #设置PROXY_LOG_LEVEL
            value: "WARN"
          - name: POD_NAME
            valueFrom: 
              fieldRef: 
                apiVersion: v1
                fieldPath: metadata.name
          volumeMounts: 
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data
            subPathExpr: $(POD_NAME)/data
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data/logs
            subPathExpr: $(POD_NAME)/log
          - name: rockmq-broker-011-config  #挂载配置文件 
            mountPath: /data/conf
          - name: rockmq-broker-acl-config  #挂载配置文件 
            mountPath: /data/conf/acl
          - name: host-time  #挂载本地时区
            mountPath: /etc/localtime
            readOnly: true
            
      volumes: 
      - name: rocketmq-volume  #使用pvc
        persistentVolumeClaim:
          claimName:  rocketmq-broker-01-pvc
      - name: host-time
        hostPath: #挂载本地时区
          path: /etc/localtime
          type: ""
      - name: rockmq-broker-011-config  #使用configMap
        configMap:    
          name: rockmq-broker-011-config
          items: 
          - key: broker.conf
            path: broker.conf
      - name: rockmq-broker-acl-config  #使用configMap
        configMap:    
          name: rockmq-broker-acl-config
          items: 
          - key: plain_acl.yml
            path: plain_acl.yml

---


apiVersion: v1
kind: ConfigMap #配置信息
metadata:
  name: rockmq-broker-010-config
  namespace:  mq
data:
  broker.conf: |
    brokerClusterName = cluster-broker-01
    #同1组主从borker需要保持一致
    brokerName = broker-010
    
    #自动主备切换模式下Broker无需指定brokerId和brokerRole,其由Controller组件进行分配
    #broker id,0 表示 master,其他的正整数表示 slave
    #brokerId = 1
    #brokerRole = ASYNC_MASTER
    
    #在每天的什么时间删除已经超过文件保留时间的 commit log
    deleteWhen = 04
    #以小时计算的文件保留时间
    fileReservedTime = 72
    #commit log 的映射文件大小 1024 * 1024 * 1024 (1G)
    mappedFileSizeCommitLog = 1024 * 1024 * 1024
    
    flushDiskType = ASYNC_FLUSH
    #启用 Controller 自动主从切换模式
    enableControllerMode = true
    #controller 的地址,多个 controller 中间用分号隔开。例如 127.0.0.1:9877;127.0.0.1:9878;127.0.0.1:9879
    controllerAddr = rocketmq-nsrv-01-svc:9877
    #向 controller 同步 Broker 副本信息的时间间隔。默认 5000(5s)。
    syncBrokerMetadataPeriod = 5000
    #检查 SyncStateSet 的时间间隔,检查 SyncStateSet 可能会 shrink SyncState。默认5000(5s)。
    checkSyncStateSetPeriod = 5000
    #同步 controller 元数据的时间间隔,主要是获取 active controller 的地址。默认10000(10s)。
    syncControllerMetadataPeriod = 10000
    #表示 Slave 没有跟上 Master 的最大时间间隔,若在 SyncStateSet 中的 slave 超过该时间间隔会将其从 SyncStateSet 移除。默认为 15000(15s)。
    haMaxTimeSlaveNotCatchup = 15000
    #存储 epoch 文件的位置。epoch 文件非常重要,不可以随意删除。默认在 store 目录下。
    storePathEpochFile = /data/epoch
    #allAckInSyncStateSet:若该值为 true,则一条消息需要复制到 SyncStateSet 中的每一个副本才会向客户端返回成功,可以保证消息不丢失。默认为 false。
    allAckInSyncStateSet = false
    #syncFromLastFile:若 slave 是空盘启动,是否从最后一个文件进行复制。默认为 false。
    syncFromLastFile = false
    #asyncLearner:若该值为 true,则该副本不会进入 SyncStateSet,也就是不会被选举成 Master,而是一直作为一个 learner 副本进行异步复制。默认为false。
    asyncLearner = false
    #inSyncReplicas:需保持同步的副本组数量,默认为1,allAckInSyncStateSet=true 时该参数无效。
    inSyncReplicas = 1
    #minInSyncReplicas:最小需保持同步的副本组数量,若 SyncStateSet 中副本个数小于 minInSyncReplicas 则 putMessage 直接返回 PutMessageStatus.IN_SYNC_REPLICAS_NOT_ENOUGH,默认为1。
    minInSyncReplicas = 1
    storePathRootDir=/data/store
    storePathCommitLog=/data/store/commitlog
    #aclEnable=true

---

apiVersion: v1
kind: ConfigMap #配置信息
metadata:
  name: rockmq-broker-011-config
  namespace:  mq
data:
  broker.conf: |
    brokerClusterName = cluster-broker-01
    #同1组主从borker需要保持一致
    brokerName = broker-010
    
    #自动主备切换模式下Broker无需指定brokerId和brokerRole,其由Controller组件进行分配
    #broker id,0 表示 master,其他的正整数表示 slave
    #brokerId = 1
    #brokerRole = ASYNC_MASTER
    
    #在每天的什么时间删除已经超过文件保留时间的 commit log
    deleteWhen = 04
    #以小时计算的文件保留时间
    fileReservedTime = 72
    #commit log 的映射文件大小 1024 * 1024 * 1024 (1G)
    mappedFileSizeCommitLog = 1024 * 1024 * 1024
    flushDiskType = ASYNC_FLUSH
    #启用 Controller 自动主从切换模式
    enableControllerMode = true
    #controller 的地址,多个 controller 中间用分号隔开。例如 127.0.0.1:9877;127.0.0.1:9878;127.0.0.1:9879
    controllerAddr = rocketmq-nsrv-01-svc:9877
    #向 controller 同步 Broker 副本信息的时间间隔。默认 5000(5s)。
    syncBrokerMetadataPeriod = 5000
    #检查 SyncStateSet 的时间间隔,检查 SyncStateSet 可能会 shrink SyncState。默认5000(5s)。
    checkSyncStateSetPeriod = 5000
    #同步 controller 元数据的时间间隔,主要是获取 active controller 的地址。默认10000(10s)。
    syncControllerMetadataPeriod = 10000
    #表示 Slave 没有跟上 Master 的最大时间间隔,若在 SyncStateSet 中的 slave 超过该时间间隔会将其从 SyncStateSet 移除。默认为 15000(15s)。
    haMaxTimeSlaveNotCatchup = 15000
    #存储 epoch 文件的位置。epoch 文件非常重要,不可以随意删除。默认在 store 目录下。
    storePathEpochFile = /data/epoch
    #allAckInSyncStateSet:若该值为 true,则一条消息需要复制到 SyncStateSet 中的每一个副本才会向客户端返回成功,可以保证消息不丢失。默认为 false。
    allAckInSyncStateSet = false
    #syncFromLastFile:若 slave 是空盘启动,是否从最后一个文件进行复制。默认为 false。
    syncFromLastFile = false
    #asyncLearner:若该值为 true,则该副本不会进入 SyncStateSet,也就是不会被选举成 Master,而是一直作为一个 learner 副本进行异步复制。默认为false。
    asyncLearner = false
    #inSyncReplicas:需保持同步的副本组数量,默认为1,allAckInSyncStateSet=true 时该参数无效。
    inSyncReplicas = 1
    #minInSyncReplicas:最小需保持同步的副本组数量,若 SyncStateSet 中副本个数小于 minInSyncReplicas 则 putMessage 直接返回 PutMessageStatus.IN_SYNC_REPLICAS_NOT_ENOUGH,默认为1。
    minInSyncReplicas = 1
    storePathRootDir=/data/store
    storePathCommitLog=/data/store/commitlog
    #aclEnable=true

---


apiVersion: v1
kind: ConfigMap #配置信息
metadata:
  name: rockmq-broker-acl-config
  namespace:  mq
data:
  plain_acl.yml: |
    globalWhiteRemoteAddresses:
      - 10.244.*.* #k8s pod ip 网段范围
      - 192.168.0.* # 宿主机ip 网段范围
    accounts:
    - accessKey: RocketMQ
      secretKey: userpassword
      whiteRemoteAddress:
      admin: false
      defaultTopicPerm: DENY
      defaultGroupPerm: SUB
      #topicPerms:
        #- topicA=DENY
        #- topicB=PUB|SUB
        #- topicC=SUB
      #groupPerms:
        # the group should convert to retry topic
        #- groupA=DENY
        #- groupB=PUB|SUB
        #- groupC=SUB

    - accessKey: RocketMQAdmin
      secretKey: userpassword
      whiteRemoteAddress: 192.168.1.*
      # if it is admin, it could access all resources
      admin: true
    

---

Rocketmq dahboard 部署

官方还提供了管理工具的
详见: rocketmq dahboard
使用官方的docker镜像,通过k8s直接部署即可,就是k8s拉取镜像的时候可能会卡,我是通过docker pull 下来以后传到私服上面给k8s使用来部署的。

  • 只要通过 ENV JAVA_OPTS 配置 nameserver的地址就行了,也不需要特别配置JVM堆参数,给容器1g内存跑起来没问题。
  • 加了个service 便于通过nginx代理访问

以下是k8s 部署文件

---

#声明存储使用
#local存储  storage_class:local-path-provisioner(rancher)
apiVersion: v1 
kind: PersistentVolumeClaim
metadata:
  name: rocketmq-dashboard-01-pvc
  namespace:  mq
spec:
  accessModes:
    - ReadWriteOnce #本地存储只支持ReadWriteOnce
  storageClassName: local-path #local-path: 容器删除,存储local-path动态删除,local-path-retain: 容器删除,存储local-path保留,local-path|local-path-retain为手动安装的storageclass
  resources:
    requests:
      storage: 5Gi #声明最少要使用存储空间,不足则无法创建 Gi=G Mi=M 
  #persistentVolumeReclaimPolicy: Delete # PVC 回收策略 Retain 保留| Delete 清除 | PV: local-path-provisioner(rancher) 不支持设置该属性
  
---


# mysql service

apiVersion: v1
kind: Service
metadata:
  name: rocketmq-dashboard-01-svc
  namespace:  mq
  annotations: 
    desc : rocketmq 01 集群 dashboard的服务访问入口
spec:
  selector:
    k8s-app: rocketmq-dashboard-01
  type: ClusterIP   #type:  ClusterIP【默认】 | NodePort | LoadBalancer(外部负载均衡) | ExternalName (外部DNS解析)
  clusterIP: 10.106.212.1
  ports:
    - port: 80
      targetPort: 8080
      name: web-port
      
---

apiVersion: apps/v1
kind: StatefulSet # Deployment | StatefulSet | DaemonSet | JobSet
metadata: 
  name:  rocketmq-dashboard-01
  namespace:   mq
spec: 
  replicas: 1  #运行副本数
  selector: 
    matchLabels: 
      k8s-app:  rocketmq-dashboard-01 #与下方template节点中的 labels 保持一致
  revisionHistoryLimit: 10 #设定保留最近的几个revision 用于回滚,默认10
  #serviceName: "nginx-headless" #设置绑定的service,以支持内部dns访问 <pod-name>.<svc-name>.<namespace>.svc.cluster.local
  updateStrategy: #更新策略 [Statefulset]
  #strategy: #更新策略 [Deployment]
    type: RollingUpdate # RollingUpdate (滚动更新) | OnDelete (删除时更新)
    rollingUpdate:
      #maxSurge: 1  #[Deployment]支持-升级过程中可以启动超过原先设置的POD数量的上限:数量 或 百分比 1 | 20%
      #maxUnavailable: 1 #[Deployment]支持-升级过程中无法提供服务的POD数量的上限:数量 或 百分比 1 | 20%,最好与maxSurge保持一致,这样能确保更新过程中的服务能力不会下降
      partition: 0 #[Statefulset] 灰度发布控制器,每次只更新部署的pod序号 >= partition的pod,如果有5个pod[0-4],0=更新所有,4=更新1pod,3=更新2pod
  template: 
    metadata: 
      labels: 
         k8s-app: rocketmq-dashboard-01
    spec: 
      #imagePullSecrets:                        #私服认证信息
      #- name: jenkins-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      restartPolicy: Always 
      terminationGracePeriodSeconds: 30 #容器被删除变为Terminating状态的等待时间,默认是30s,以便于做一些容器删除前的处理工作
      #imagePullSecrets:                        #私服认证信息
      #- name: local-registry-key                  #私服账号secret资源名称,需要单独创建:kubectl create secret generic... 详见:https://kubernetes.io/zh-cn/docs/tasks/configure-pod-container/pull-image-private-registry/
      #initContainers:
      #- name: init-deploy
      #  image: 8.0.36
      #  command: 
      #  - "sh" 
      #  - "-c"
      #  - >  # 初始化用于部署的文件资源
      #    cd /data/deploy;
      #  volumeMounts:
      #  - name: api-admin-volume  #挂载部署目录
      #    mountPath: /data/deploy
      #    subPath: deploy
      containers:  
        - name: rocketmq-dashboard-01
          image: apacherocketmq/rocketmq-dashboard:latest
          imagePullPolicy: IfNotPresent # IfNotPresent | Always | Never
          resources:
            requests:
              memory: "1Gi" #Gi=G Mi=M 只支持整数
              #cpu: "1000m" #1000m=1cpu (cpu物理线程)
            limits:
              memory: "1Gi" #Gi=G Mi=M 只支持整数
              cpu: "1000m"  #1000m=1cpu (cpu物理线程)
          #securityContext: ###添加参数启用容器root权限
          #  privileged: true
          ports: 
          - containerPort: 8080
            protocol: TCP
          #startupProbe: #容器启动探针,失败自动重启 结果Success:表示通过检测| Failure:表示未通过检测|Unknown:表示检测没有正常进行。 
          #  tcpSocket:
          #    port: 9876
          #  initialDelaySeconds: 10 #容器启动后要等待多少秒后就探针开始工作,单位“秒”,默认是 0 秒,最小值是 0
            #periodSeconds: 10 #执行探测的时间间隔(单位是秒),默认为 10s,单位“秒”,最小值是 1
            #timeoutSeconds: 2 #探针执行检测请求后,等待响应的超时时间,默认为 1s,单位“秒”,最小值是 1
            #successThreshold: 1 #探针检测失败后认为成功的最小连接成功次数,默认为 1s,在 Liveness 探针中必须为 1,最小值为 1。
            #failureThreshold: 3 #探测失败的重试次数,重试一定次数后将认为失败,在 readiness 探针中,Pod会被标记为未就绪,默认为 3,最小值为 1
          #lifecycle:
          #  postStart:  #通过postStart 钩子函数做初始化|如果失败会重启容器
          #    exec: 
          #      command: # 设置/etc/nginx/nginx.conf - /data/nginx/nginx.conf的软连接
          #        - "sh" 
          #        - "-c"
          #        - >  # 设置registry垃圾回收器的定时任务,清理日志的定时任务并启动调度服务
          #          rm -f /etc/nginx/nginx.conf;
          #          ln -s /data/nginx/nginx.conf /etc/nginx/nginx.conf;
          #          nginx -s reload 
          #command: ["/bin/sh","-c"] #添加registry垃圾回收定时任务,并启动系统定时调度服务
          #args: #可以设置多行命令,不过启动后初始化还是推荐使用postStart钩子函数来执行,不能有#注释符
          #ln -s /data/conf/acl/acl.yml /usr/local/rocketmq/conf/acl.yml;
          #- | 
          #
          #  mqbroker -c /data/conf/broker.conf -n rocketmq-nsrv-01-svc:9876 --enable-proxy 
          env:   #环境变量配置
          - name: JAVA_OPTS
            value: "-Drocketmq.namesrv.addr=rocketmq-nsrv-01-svc:9876"
          - name: POD_NAME
            valueFrom: 
              fieldRef: 
                apiVersion: v1
                fieldPath: metadata.name
          volumeMounts: 
          - name: rocketmq-volume  #挂载部署目录
            mountPath: /data
            subPath: data
            #subPathExpr: $(POD_NAME)/data
          #- name: rockmq-broker-010-config  #挂载配置文件 
          #  mountPath: /data/conf
          - name: host-time  #挂载本地时区
            mountPath: /etc/localtime
            readOnly: true
            
      volumes: 
      - name: rocketmq-volume  #使用pvc
        persistentVolumeClaim:
          claimName:  rocketmq-dashboard-01-pvc
      - name: host-time
        hostPath: #挂载本地时区
          path: /etc/localtime
          type: ""
      #- name: rockmq-broker-010-config  #使用configMap
      #  configMap:    
      #    name: rockmq-broker-010-config
      #    items: 
      #    - key: broker.conf
      #      path: broker.conf


---

部署好的界面
在这里插入图片描述
这就是我通过上面的k8s部署文件部署好的的集群

好了,说到这里,本文结束,真是挺长的,我写了2个多小时,鞠躬下台。

--------------------- 原创不易,如果大家看完觉得有帮助,希望能多多点赞关注,感谢各位的支持 ----------------------

  • 15
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

windywolf301

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值