You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

K8s StatefulSet中MongoDB重启后数据及副本集配置丢失问题

部署配置

1. Service配置(注意:存在重复定义,建议合并)

---
apiVersion: v1 
kind: Service 
metadata: 
  namespace: mongodb 
  name: mongodb
  annotations:
    service.beta.kubernetes.io/azure-load-balancer-internal: "true"
spec: 
  type: LoadBalancer 
  ports: 
  - protocol: TCP 
    port: 27017 
    targetPort: 27017 
  selector: 
    app: mongodb

---
apiVersion: v1 
kind: Service 
metadata: 
  namespace: mongodb 
  name: mongodb
  annotations:
    service.beta.kubernetes.io/azure-load-balancer-internal: "true"
spec: 
  type: LoadBalancer 
  ports: 
  - protocol: TCP 
    port: 27017 
    targetPort: 27017 
  selector: 
    app: mongodb

2. StatefulSet配置

---
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: mongodb
  namespace: mongodb
spec:
  selector:
    matchLabels:
      app: mongodb
  serviceName: mongodb
  replicas: 3
  template:
    metadata:
      labels:
        app: mongodb
    spec:
      containers:
        - name: mongodb
          image: private-repo/mongo:7.0
          imagePullPolicy: Always
          args:
            - --bind_ip_all
            - --replSet
            - rs0
            - --dbpath
            - /data/db
            - --keyFile
            - /etc/mongo/keyfile
            - --setParameter
            - authenticationMechanisms=SCRAM-SHA-256 
            - --auth
            - --wiredTigerCacheSizeGB
            - "6"
          ports:
          - name: mongodb
            containerPort: 27017
          volumeMounts:
          - name: mongodb-pvc 
            mountPath: /data
          envFrom:
          - configMapRef:
              name: mongodb
          - secretRef:
              name: mongodb
  volumeClaimTemplates:
  - metadata:
      name: mongodb-pvc 
      namespace: mongodb 
    spec:
      accessModes: ["ReadWriteOnce"]
      storageClassName: premium-retain
      resources:
        requests:
          storage: 256Gi

3. Secret配置

---
apiVersion: v1 
kind: Secret 
metadata: 
  name: mongodb 
  namespace: mongodb
type: Opaque
stringData:
  MONGO_INITDB_ROOT_USERNAME: "USERNAME"
  MONGO_INITDB_ROOT_PASSWORD: "PASSWORD"
  MONGO_INITDB_DATABASE: "db"

4. ConfigMap配置

---
apiVersion: v1
kind: ConfigMap
metadata:
  name: mongodb
  namespace: mongodb
  labels:
    app: mongodb
data:
  ENV: "prod"

5. Dockerfile

FROM mongo:7.0

COPY /mongodb-keyfile /etc/mongo/keyfile
RUN chown -R 999:999 /etc/mongo/keyfile
RUN chmod 400 /etc/mongo/keyfile

问题原因分析及解决方案

核心原因

  1. 副本集配置存储损坏:MongoDB副本集的配置信息存在local数据库中,该库与业务数据同存于/data/db目录。磁盘IO饱和导致Pod崩溃时,local库的WiredTiger元数据文件可能损坏,重启后MongoDB无法加载副本集配置,进入未初始化状态,即使业务数据文件完好也无法识别。

  2. 全量重启导致集群无有效配置源:无论是Deployment还是StatefulSet,当所有Pod同时重启时,没有节点能提供可用的副本集配置,每个节点都会认为自己是新节点,无法自动恢复集群。

  3. 磁盘压力触发的数据一致性问题:导入数据时IO过载,可能触发WiredTiger的故障保护,导致部分数据文件(尤其是元数据)损坏,MongoDB重启后无法自动修复,只能重新初始化。

解决方案

  • 优化磁盘IO性能:

    • 确认存储类premium-retain的IOPS配额满足导入需求,必要时临时调高配额,或分批导入数据降低IO压力。
    • 调整wiredTigerCacheSizeGB参数,避免缓存占用过多内存引发磁盘交换,进一步加剧IO负载。
  • 避免全量Pod重启:

    • 对StatefulSet执行滚动重启,每次仅重启一个Pod,确保集群始终有可用节点提供配置。
    • 添加优雅关闭配置,给MongoDB足够时间完成数据刷盘:
      spec:
        template:
          spec:
            terminationGracePeriodSeconds: 300
            containers:
              - name: mongodb
                lifecycle:
                  preStop:
                    exec:
                      command: ["mongosh", "--eval", "db.adminCommand({ shutdown: 1, force: false })"]
      
  • 手动恢复配置与数据:
    当业务数据文件完好但副本集配置丢失时:

    1. 停止所有MongoDB Pod,仅启动一个节点,添加--noReplSet参数以单实例模式启动。
    2. 登录MongoDB,删除损坏的local.system.replset集合,然后执行rs.initiate()重新初始化副本集,此时业务数据会被保留。
  • 备份副本集配置:
    定期执行rs.conf()导出副本集配置并存储到外部,集群配置丢失时可快速导入恢复。


内容的提问来源于stack exchange,提问作者Dimi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 19:44:51