2024 Kubernetes生产实践:从声明式交付到多集群协同
1. 这不是又一本K8s入门书——为什么2024年学Kubernetes必须换套方法“Learning Kubernetes the Right Way In 2024”这个标题乍看像营销话术但我在过去三年带过47个企业级K8s落地项目、给21家中小技术团队做过架构复盘后越来越确信2024年还在照着2018年那套“kubectl run YAML三件套 Helm chart模板”学Kubernetes的人不是学得慢而是从根上就踩进了三个认知陷阱。第一个陷阱是把K8s当成“更高级的Docker Compose”——结果部署完发现服务连不上、日志查不到、扩缩容像开盲盒第二个陷阱是沉迷于组件名词解释背熟etcd、kube-apiserver、CNI、CSI这些词却写不出一份能通过kubectl apply --dry-runclient -o wide校验的Production-ready Deployment第三个陷阱最隐蔽用Kind或Minikube搭个单节点集群就以为“已掌握”等真上云厂商托管集群比如EKS/GKE/AKS时才发现RBAC策略不生效、Pod Security Admission被默认拦截、NetworkPolicy根本没生效——因为本地环境压根没模拟真实生产约束。我试过让一位有5年Java开发经验的工程师只用官方文档Katacoda沙箱学两周K8s结果他能熟练写StatefulSet却在真实CI/CD流水线里卡在Service Account Token自动轮转失败上整整三天。问题不在他而在学习路径本身2024年的K8s生态早已不是“会部署就行”的阶段而是“默认安全、声明即契约、可观测性内建、多集群协同”成为基线要求。你不需要从源码编译kubelet开始但必须清楚知道当你写securityContext.runAsNonRoot: true时底层PodSecurityPolicy已弃用和Pod Security Admissionv1.25默认启用如何协同拦截违规Pod当你配置service.spec.externalTrafficPolicy: Local时云厂商LoadBalancer如何与NodePort、EndpointSlice联动当你用kubectl get events --sort-by.lastTimestamp排查问题时事件对象里的reason: FailedScheduling背后到底是资源不足、污点不匹配还是VolumeBindingMode延迟触发。这篇文章就是为那些已经写过YAML、跑过Pod、但一进真实环境就掉链子的开发者写的。它不讲“什么是容器”不重复kubectl get pods -A基础命令而是直接切入2024年生产环境里每天都在发生的12类高频场景从零构建符合CIS Kubernetes Benchmark v1.8.0的最小权限集群到用OpenTelemetry Collector统一采集指标/日志/链路再到用KustomizeKpt实现GitOps驱动的渐进式发布。所有内容都基于我亲手在AWS EKS 1.28、Azure AKS 1.27、以及自建K3s 1.28集群上验证过的实操步骤。你可以把它当作一份“避坑地图”也可以当作战地手册——重点不是告诉你“该做什么”而是让你明白“为什么必须这么做”“不做会怎样”“别人踩过的坑长什么样”。2. 学习路径重构从“组件罗列”到“能力分层”的四阶跃迁2.1 为什么传统学习路径在2024年彻底失效2016年K8s刚火时学习路径很清晰先学Docker再学Pod/Deployment/Service最后配个Ingress。那时etcd是黑盒CNI插件选Flannel就行安全靠iptables硬扛。但2024年Kubernetes项目本身已进入稳定期v1.28是最后一个带alpha API的版本而周边生态却爆炸式演进。我统计了近半年客户生产集群的配置变更记录发现83%的故障源于“新旧能力叠加冲突”比如某金融客户升级到EKS 1.27后所有Pod启动失败日志只显示container runtime error排查三天才发现是他们沿用的旧版containerd配置未启用systemd_cgroup true导致cgroup v2下OOM Killer行为异常——而这个问题在2022年之前的文档里根本不会提。更关键的是K8s的“能力边界”正在快速上移。以前你需要自己写脚本轮询API Server获取Pod状态现在kubectl wait --forconditionReady pod/my-app原生支持以前用Prometheus Operator手动管理ServiceMonitor现在K8s 1.27原生支持metrics.k8s.io/v1beta1聚合API以前调试网络全靠tcpdump抓包现在kubectl debug内置Ephemeral Containers甚至支持--share-processes直接进目标容器命名空间。这意味着2024年学K8s核心不是记忆组件名而是建立“能力分层认知模型”——把K8s看作一个分层操作系统每一层解决一类确定性问题且层与层之间有明确契约。提示不要试图一次性搞懂所有组件。etcd、kube-scheduler、cloud-controller-manager这些组件你只需要知道“它负责什么”“出问题时看什么日志”“重启是否影响业务”而不是去研究Raft协议细节或调度算法源码。真正的生产价值永远在“能力层”而非“组件层”。2.2 四阶能力跃迁模型每个阶段对应真实工作场景我把2024年K8s能力划分为四个递进层级每个层级对应一类典型工作负载和故障场景。这不是理论分级而是我从47个项目中提炼出的“能力断点图谱”第一阶声明式交付Declarative Delivery目标写出能通过kubectl apply --dry-runserver -o yaml | kubectl diff零差异的YAML且一次通过CI/CD流水线。核心能力精确控制spec.replicas与status.replicas的收敛逻辑理解ProgressDeadlineSeconds如何触发RollingUpdate回滚区分initContainers与containers的启动时序约束比如证书生成必须在应用容器启动前完成掌握volumeMounts.subPath与subPathExpr的适用场景避免ConfigMap热更新时整个Pod重启典型故障某电商大促前上线新版本因livenessProbe.initialDelaySeconds设为5秒实际应用冷启动需12秒导致Pod反复重启进入CrashLoopBackOff。第二阶运行时治理Runtime Governance目标在Pod运行中动态干预、诊断、修复不依赖重建。核心能力使用kubectl debug注入调试容器并共享进程命名空间--share-processes通过kubectl top nodes/pods结合kubectl describe node定位资源争抢如CPU Throttling、Memory Pressure利用kubectl get events --field-selector involvedObject.namemy-pod过滤精准事件流典型故障某SaaS平台用户反馈API响应慢kubectl top pods显示CPU使用率仅30%但kubectl describe pod暴露出QoS Class: Burstable且Limits.cpu设为1而实际请求峰值达1.8核——本质是资源限制不合理非代码性能问题。第三阶安全基线Security Baseline目标集群通过CIS Kubernetes Benchmark v1.8.0全部132项检查且无误报。核心能力配置Pod Security AdmissionPSA的enforce/audit/warn三级策略不再依赖已废弃的PodSecurityPolicy实现ServiceAccount最小权限原则禁用defaultSA为每个Namespace创建专用SA并绑定Role启用--enable-admission-pluginsNodeRestriction,PodSecurity,EventRateLimit等关键准入控制器典型故障某政务系统上线后遭渗透测试发现所有Pod默认以root运行且可挂载宿主机敏感路径——根源是未启用PSA且Deployment中未设置securityContext.runAsNonRoot: true和securityContext.privileged: false。第四阶多集群协同Multi-Cluster Orchestration目标跨公有云/私有云/边缘节点统一发布、观测、策略执行。核心能力使用Karmada或Cluster APICAPI实现集群生命周期管理通过Open Policy AgentOPA Gatekeeper定义跨集群一致的合规策略如“所有生产Namespace必须启用PSA enforce”利用Service MeshIstio/Linkerd实现跨集群服务发现与流量治理典型故障某跨国零售企业部署全球多集群因各区域集群NetworkPolicy规则不一致导致亚太区支付服务无法调用欧洲区风控服务——表面是网络不通实则是策略治理缺失。这四阶不是线性学习顺序而是能力坐标系。你在做CI/CD流水线时可能卡在第一阶在排查线上慢查询时需要第二阶能力在通过等保测评时必须达到第三阶在设计全球化架构时则直奔第四阶。本文后续所有实操都严格按此模型组织。3. 核心实操从零构建符合2024生产标准的K8s集群3.1 环境准备为什么放弃Minikube/KinD选择K3s作为学习底座很多教程推荐Minikube或KinD起步理由是“轻量易上手”。但我在2023年对12个学员做对比实验后发现用Minikube学完的学员在真实EKS集群上首次部署失败率高达76%而用K3sv1.28.5k3s2的学员失败率降至21%。差距在哪根本原因在于组件栈一致性。Minikube默认用Docker作为容器运行时KinD用containerd但禁用cgroup v2而95%的生产环境包括EKS/GKE/AKS已强制启用cgroup v2 containerd systemd cgroup driver。K3s则完美复刻这一栈它内置containerd 1.7.13默认启用systemd_cgroup true且所有组件包括traefik ingress controller、local-path storage provisioner都经过cgroup v2压力测试。更重要的是K3s的“精简但不失真”特性。它移除了kubelet的--cloud-provider参数因无云厂商集成但保留了完整的--node-labels、--register-with-taints、--feature-gates等生产级参数。这意味着你在K3s上配置的nodeSelector、tolerations、RuntimeClass在EKS上100%可用。而Minikube的--cpus参数只是虚拟化CPU配额与K8s真实的resources.requests.cpu语义完全不同。实操步骤如下以Ubuntu 22.04 LTS为例全程离线可操作# 步骤1关闭swapK8s强制要求 sudo swapoff -a sudo sed -i / swap / s/^\(.*\)$/#\1/g /etc/fstab # 步骤2启用cgroup v2Ubuntu 22.04默认已启用但需确认 cat /proc/filesystems | grep cgroup # 应输出nodev cgroup2 # 步骤3安装K3sv1.28.5k3s22024年Q2最新LTS curl -sfL https://get.k3s.io | sh -s - \ --write-kubeconfig-mode 644 \ --disable traefik \ --disable local-storage \ --disable-network-policy \ --kubelet-arg feature-gatesServerSideApplytrue,PodSecuritytrue \ --kube-apiserver-arg enable-admission-pluginsNodeRestriction,PodSecurity,EventRateLimit # 步骤4等待服务就绪约15秒 sudo systemctl status k3s # 步骤5配置kubectl自动读取/etc/rancher/k3s/k3s.yaml export KUBECONFIG/etc/rancher/k3s/k3s.yaml kubectl get nodes -o wide # 输出应显示Ready control-plane 2m v1.28.5k3s2注意--disable traefik不是不要Ingress而是避免学习初期被Ingress Controller的复杂配置干扰。我们后续用原生Service typeLoadBalancer配合MetalLB模拟云厂商LB行为。--disable local-storage是因为生产环境绝不用本地存储必须显式对接外部存储如NFS/Ceph。--kubelet-arg feature-gatesPodSecuritytrue是关键——它启用Pod Security AdmissionPSA这是2024年安全基线的基石。3.2 第一阶实战编写零差错Deployment的7个黄金法则写一个能跑起来的Deployment很简单但写一个“永不因配置缺陷导致线上事故”的Deployment需要掌握7个反直觉细节。这些不是最佳实践清单而是我从21次线上P0事故复盘中提炼的血泪教训。法则1永远用strategy.rollingUpdate.maxSurge和maxUnavailable显式声明错误写法strategy: type: RollingUpdate正确写法strategy: type: RollingUpdate rollingUpdate: maxSurge: 25% maxUnavailable: 0为什么maxUnavailable: 0确保滚动更新期间服务始终有副本在线避免ReadinessProbe失败导致流量中断maxSurge: 25%限制额外Pod数量防止资源超卖。某支付系统曾因未设maxUnavailable更新时所有Pod同时终止造成3分钟全站不可用。法则2livenessProbe和readinessProbe必须分离且参数独立错误写法livenessProbe: httpGet: path: /healthz port: 8080 initialDelaySeconds: 10 periodSeconds: 10 readinessProbe: httpGet: path: /healthz port: 8080 initialDelaySeconds: 10 periodSeconds: 10正确写法livenessProbe: httpGet: path: /livez port: 8080 initialDelaySeconds: 30 # 冷启动时间 periodSeconds: 30 # 避免频繁重启 failureThreshold: 3 # 连续3次失败才重启 readinessProbe: httpGet: path: /readyz port: 8080 initialDelaySeconds: 5 # 快速就绪 periodSeconds: 2 # 高频探测保障流量不打到未就绪Pod failureThreshold: 1 # 1次失败立即摘除流量/livez和/readyz是K8s官方推荐的健康端点分离模式。livenessProbe失败会重启PodreadinessProbe失败只摘流量——二者目标完全不同参数必须差异化设计。法则3resources.requests和limits必须成对出现且requests limits用于Guaranteed QoS错误写法resources: requests: memory: 512Mi limits: memory: 1Gi正确写法对关键服务resources: requests: memory: 1Gi cpu: 500m limits: memory: 1Gi cpu: 500mK8s QoS分为Guaranteed、Burstable、BestEffort三级。只有requests limits才是Guaranteed意味着Pod绝不会被OOM Killer优先杀死。某AI训练平台因未设requests所有训练Pod被系统随机OOM导致数小时训练成果丢失。法则4securityContext必须包含runAsNonRoot、runAsUser、fsGroup三要素错误写法securityContext: runAsNonRoot: true正确写法securityContext: runAsNonRoot: true runAsUser: 1001 runAsGroup: 1001 fsGroup: 1001 seccompProfile: type: RuntimeDefaultrunAsUser指定非root UID避免容器内进程以root身份运行fsGroup确保挂载卷的文件属组正确否则ConfigMap/Secret挂载后应用无法读取seccompProfile.type: RuntimeDefault启用运行时默认安全策略containerd 1.7默认支持。法则5volumeMounts必须用subPath而非挂载整个ConfigMap/Secret错误写法volumeMounts: - name: config mountPath: /app/config volumes: - name: config configMap: name: app-config正确写法volumeMounts: - name: config mountPath: /app/config/app.yaml subPath: app.yaml volumes: - name: config configMap: name: app-config整ConfigMap挂载会导致Pod在ConfigMap更新时被强制重启K8s机制。subPath只挂载单个键更新ConfigMap时Pod不重启应用自行热加载。法则6envFrom必须配合prefix避免环境变量污染错误写法envFrom: - configMapRef: name: db-config正确写法envFrom: - configMapRef: name: db-config prefix: DB_envFrom会将ConfigMap所有键转为环境变量极易与系统变量如PATH、HOME冲突。加prefix隔离命名空间是生产环境铁律。法则7terminationGracePeriodSeconds必须设为30-60秒且应用必须监听SIGTERM错误写法terminationGracePeriodSeconds: 30正确写法terminationGracePeriodSeconds: 60 lifecycle: preStop: exec: command: [/bin/sh, -c, sleep 30]preStop钩子确保应用有足够时间优雅关闭连接、刷盘数据。terminationGracePeriodSeconds是总宽限期preStop是其中一部分。某消息队列因未设preStopPod终止时未ACK消息导致10万条消息重复投递。3.3 第二阶实战用kubectl debug进行无侵入式故障诊断kubectl debug是K8s 1.20正式GA的功能但它远不止“进容器看看”那么简单。2024年的真实价值在于它让你在不修改原始Pod定义、不重启服务的前提下获得与生产Pod完全一致的运行时上下文。我用它解决过最棘手的三个问题SSL证书链验证失败、gRPC连接超时、内存泄漏定位。场景1诊断SSL证书链问题无需暴露应用端口某微服务调用第三方API时持续报x509: certificate signed by unknown authority但curl -v https://api.example.com在Pod内正常。问题出在应用使用的TLS库如Go net/http默认不读取/etc/ssl/certs/ca-certificates.crt而curl会读。用kubectl debug注入调试容器复现# 创建调试容器基于ubuntu:22.04预装openssl/curl kubectl debug -it my-pod \ --imageubuntu:22.04 \ --share-processes \ --copy-tomy-pod-debug # 在调试容器内执行复现应用TLS环境 chroot /proc/1/root /bin/bash -c openssl s_client -connect api.example.com:443 -showcerts # 输出显示证书链不完整证实是应用TLS库配置问题非集群网络问题场景2抓取gRPC连接的HTTP/2帧无需修改应用代码某服务gRPC调用超时kubectl logs无异常。用kubectl debug注入Wireshark兼容环境# 注入含tcpdump的容器 kubectl debug -it my-pod \ --imagenicolaka/netshoot \ --share-processes \ --copy-tomy-pod-netdebug # 抓取Pod内所有gRPC流量端口50051 tcpdump -i any -w /tmp/grpc.pcap port 50051 # 将pcap文件导出到本地分析 kubectl cp my-namespace/my-pod-debug:/tmp/grpc.pcap ./grpc.pcapWireshark打开pcap过滤http2发现HEADERS帧中:authority字段为空——根源是gRPC客户端未设置WithAuthority选项。场景3实时监控内存分配替代JVM堆dumpJava应用内存持续增长但jstat显示老年代未满。用kubectl debug注入jcmd环境# 注入含JDK的容器复用Pod的JVM kubectl debug -it my-pod \ --imageadoptopenjdk/openjdk11:jre-11.0.11_9-alpine-jre \ --share-processes \ --copy-tomy-pod-jdkdebug # 查看JVM进程ID与原Pod相同 ps aux | grep java # 执行实时内存分析 jcmd 1 VM.native_memory summary # 输出显示Internal内存占用飙升指向Netty Direct Buffer泄漏实操心得--share-processes是kubectl debug的灵魂参数。它让调试容器与目标Pod共享PID namespace从而能ps aux看到原Pod所有进程用jstack/jmap/strace直接操作。没有它你只能在调试容器里“隔空喊话”效率降低80%。4. 安全基线实战用Pod Security AdmissionPSA构建零信任集群4.1 PSA不是新功能而是2024年K8s安全的“操作系统级开关”PodSecurityPolicyPSP已在K8s v1.25正式废弃其继任者Pod Security AdmissionPSA不是简单的功能替换而是安全模型的根本重构。PSP是“全局白名单”管理员定义允许的特权PSA是“命名空间级策略”每个Namespace可独立配置enforce/audit/warn三级策略且策略由K8s原生实现无需额外组件。这意味着2024年安全不再是“加个插件”而是“开个开关”。PSA的三大策略级别对应不同风险容忍度enforce违反策略的Pod创建请求被直接拒绝HTTP 403这是生产环境唯一可接受的级别。audit违规Pod允许创建但记录审计日志kubectl get events可见Warning PodSecurityViolation用于策略灰度验证。warn仅向客户端返回警告信息不阻断创建适合开发环境教育。PSA策略本身由三个维度定义privileged特权容器、baseline基线安全、restricted严格限制。这不是等级制而是能力集——restricted包含baseline所有规则baseline包含privileged所有规则。例如restricted要求runAsNonRoot: true且seccompProfile.type: RuntimeDefault而baseline只要求runAsNonRoot: true。4.2 三步启用PSA从零配置到CIS合规步骤1为Namespace打标签激活PSA策略PSA不通过RBAC或CRD配置而是通过Namespace标签控制。这是2024年最反直觉的设计——安全策略由元数据驱动。# 创建生产Namespace并打标签enforce restricted策略 kubectl create namespace prod kubectl label --overwrite ns prod \ pod-security.kubernetes.io/enforcerestricted \ pod-security.kubernetes.io/enforce-versionv1.28 \ pod-security.kubernetes.io/auditrestricted \ pod-security.kubernetes.io/audit-versionv1.28 \ pod-security.kubernetes.io/warnrestricted \ pod-security.kubernetes.io/warn-versionv1.28 # 验证标签生效 kubectl get ns prod -o yaml | grep pod-security # 应输出所有6个标签步骤2编写符合restricted策略的Deployment启用PSA后任何违反restricted规则的YAML都会被拒绝。以下是必须满足的12项核心规则基于CIS v1.8.0apiVersion: apps/v1 kind: Deployment metadata: name: secure-app namespace: prod # 必须在打标Namespace内 spec: template: spec: # 规则1禁止privileged容器 securityContext: runAsNonRoot: true # 规则2必须非root运行 runAsUser: 1001 # 规则3必须指定UID runAsGroup: 1001 # 规则4必须指定GID fsGroup: 1001 # 规则5必须指定fsGroup seccompProfile: # 规则6必须启用seccomp type: RuntimeDefault # 规则7禁止hostPID/hostIPC/hostNetwork hostPID: false hostIPC: false hostNetwork: false containers: - name: app image: nginx:1.25 # 规则8禁止添加危险capabilities securityContext: capabilities: drop: [ALL] # 必须显式drop ALL # 规则9禁止挂载敏感宿主机路径 volumeMounts: - name: config mountPath: /etc/nginx/conf.d readOnly: true # 规则10必须设置resources.limits resources: limits: memory: 512Mi cpu: 500m requests: memory: 512Mi cpu: 500m volumes: - name: config configMap: name: nginx-config # 规则11ConfigMap必须readOnly挂载 defaultMode: 0444 # 规则12必须使用ServiceAccount且不能是default serviceAccountName: prod-sa步骤3验证PSA策略效果与CIS合规扫描启用PSA后用kubectl auth can-i无法检测策略因PSA非RBAC必须用真实创建测试# 测试1尝试创建违反restricted的Pod应失败 kubectl apply -f - EOF apiVersion: v1 kind: Pod metadata: name: bad-pod namespace: prod spec: securityContext: privileged: true # 明确违反restricted containers: - name: nginx image: nginx EOF # 输出Error from server (Forbidden): error when creating STDIN: # pods bad-pod is forbidden: violates PodSecurity prod:restricted:latest # 测试2运行CIS Benchmark扫描使用kube-bench kubectl run cis-scan --rm -i --tty --imageaquasec/kube-bench:latest \ --restartNever -- --benchmark cis-1.8 # 扫描结果应显示PASS率100%重点关注1.2.1 Ensure that the --allow-privileged argument is set to false注意PSA的enforce-version必须与集群K8s版本严格匹配。K3s v1.28.5对应v1.28若设为v1.27会导致策略不生效。这是2024年最常踩的坑——版本号不是语义化版本而是PSA策略定义的快照版本。5. 多集群协同实战用Karmada实现跨云服务发现5.1 为什么Karmada是2024年多集群的事实标准当企业说“我们要多集群”90%的情况不是为了高可用而是为了合规隔离如GDPR要求欧盟数据不出境、成本优化如Spot实例跑批处理OnDemand实例跑核心服务、灾备演练定期切换主备集群。但2023年之前多集群方案要么太重Red Hat OpenShift ACM要么太轻自研脚本同步YAML直到Karmada v1.52024年3月发布成熟。它不管理集群生命周期那是Cluster API的事专注做一件事声明式多集群资源分发与策略治理。Karmada的核心抽象是PropagationPolicy分发策略和OverridePolicy覆盖策略。前者决定“资源发到哪些集群”后者决定“在目标集群怎么改”。这比Istio的多集群ServiceEntry或Linkerd的Multicluster更底层、更通用——它工作在K8s API层不依赖特定网络插件。5.2 三集群实战AWS EKS Azure AKS 本地K3s的统一服务网格我们构建一个真实场景某SaaS平台需在AWS主站、Azure备份、K3s开发三个集群部署同一套微服务并实现主站流量100%走AWS备份集群仅接收1%探针流量所有集群共享同一套Prometheus告警规则开发集群自动禁用PSAenforce仅保留audit步骤1部署Karmada控制平面单节点5分钟Karmada提供一键部署脚本但必须注意2024年关键配置# 克隆Karmada v1.5 git clone --branch release-1.5 https://github.com/karmada-io/karmada.git cd karmada # 部署控制平面使用etcd单节点生产环境请用HA etcd ./hack/local-up-karmada.sh # 验证 kubectl --kubeconfig ~/.kube/karmada.config get clusters # 应输出No resources found in default namespace. # 尚未注册成员集群步骤2注册三个成员集群Karmada不代理API Server通信而是让成员集群主动注册类似K3s agent模式这是2024年最安全的架构# 注册AWS EKS集群假设eksctl创建 kubectl --kubeconfig ~/.kube/eks-config get nodes # 记录EKS集群名aws-prod karmadactl join aws-prod \ --cluster-kubeconfig ~/.kube/eks-config \ --cluster-context arn:aws:eks:us-west-2:123456789012:cluster/aws-prod # 注册Azure AKS集群 karmadactl join azure-backup \ --cluster-kubeconfig ~/.kube/aks-config \ --cluster-context myResourceGroup/myAKSCluster # 注册本地K3s集群 karmadactl join k3s-dev \ --cluster-kubeconfig /etc/rancher/k3s/k3s.yaml \ --cluster-context default # 验证注册状态 kubectl --kubeconfig ~/.kube/karmada.config get clusters # 应输出aws-prod, azure-backup, k3s-dev 状态为Ready步骤3编写跨集群Deployment与PropagationPolicy核心是让同一份YAML在不同集群产生不同效果# 文件1base-deployment.yaml基础定义无集群特异性 apiVersion: apps/v1 kind: Deployment metadata: name: user-service namespace: default spec: replicas: 3 selector: matchLabels: app: user-service template: metadata: labels: app: user-service spec: containers: - name: app image: my-registry/user-service:v2.4 ports: - containerPort: 8080 --- # 文件2propagation-policy.yaml分发策略 apiVersion: policy.karmada.io/v1alpha1 kind: PropagationPolicy metadata: name: user-service-propagation spec: resourceSelectors: - apiVersion: apps/v1 kind: Deployment name: user-service placement: clusterAffinity: clusterNames: - aws-prod - azure-backup - k3s-dev replicaScheduling: replicaDivisionPreference: Weighted replicaSchedulingType: Divided weightPreference: staticWeightList: - targetCluster: clusterNames: - aws-prod weight: 100 - targetCluster: clusterNames: - azure-backup weight: 1 - targetCluster: clusterNames: - k3s-dev weight: 0步骤4用OverridePolicy实现集群差异化配置这才是Karmada的精髓——同一份Deployment在AWS集群启用PSAenforce在K3s集群降级为audit# 文件3override-policy.yaml apiVersion: policy.karmada.io/v1alpha1 kind: OverridePolicy metadata: name: psa-override spec: resourceSelectors: - apiVersion: apps/v1 kind: Deployment name: user-service overriders: plaintext: - path: /spec/template/spec/securityContext/runAsNonRoot operator: replace value: true - path: /metadata/labels operator: add value: pod-security.kubernetes.io/enforce: restricted targetCluster: clusterNames: - aws-prod --- apiVersion: policy.karmada.io/v1alpha1 kind: OverridePolicy metadata: name: psa-dev-override spec: resourceSelectors: - apiVersion: apps/v1 kind: Deployment name: user-service overriders: plaintext: - path: /metadata/labels operator: add value: pod-security.kubernetes