在容器化时代,将应用打包成 Docker 镜像并运行起来并不难。但当一个系统包含数百个微服务、数千个容器时,仅仅依靠 Docker 和脚本是远远不够的。我们需要一个能够自动部署、自动伸缩、自动恢复的编排系统。Kubernetes 正是为了解决这些大规模容器编排问题而生的。
控制平面组件:
工作节点组件:
# 查看控制平面组件状态
kubectl get --raw='/readyz?verbose'
# 查看集群节点
kubectl get nodes
# 查看控制平面 Pod (在 kube-system 命名空间)
kubectl get pods -n kube-system
# 查看 API 服务器版本
kubectl version
Kubernetes 控制平面由多个组件组成,每个组件负责一个特定的职责。它们相互配合,共同维护集群的期望状态。理解这些组件的功能和交互方式,是掌握 Kubernetes 核心原理的基础。
kube-apiserver: 集群的唯一入口,所有组件通过它通信。它负责认证、鉴权、准入控制,将请求写入 etcd 并返回结果。
etcd: 分布式键值存储,集群状态的唯一真相来源。支持watch 机制,控制器和调度器可以监听状态变化。
kube-controller-manager: 运行多个控制器,每个控制器关注一种资源(如 Deployment、ReplicaSet),持续将实际状态向期望状态对齐。
kube-scheduler: 负责调度 Pod,通过过滤和打分算法选择最合适的节点。
# 查看 API 服务器健康状态
kubectl get --raw /healthz
# 查看 etcd 健康状态 (需在 etcd 容器中执行)
kubectl exec -n kube-system etcd-... -- etcdctl endpoint health
# 查看控制器管理器状态
kubectl get --raw /healthz/controller-manager
# 查看调度器状态
kubectl get --raw /healthz/scheduler
当用户创建一个 Pod 时,Kubernetes 需要决定将该 Pod 分配到哪个节点上。调度器就是负责这个决策的组件。它需要综合考虑资源需求(CPU、内存)、约束条件(节点亲和性、污点容忍)、负载均衡等因素,选择一个最优的节点。
调度阶段:
# 查看 Pod 调度情况
kubectl describe pod my-pod | grep -A 5 Events
# 查看调度器日志
kubectl logs -n kube-system kube-scheduler-... -f
# 手动调度 (用于调试)
kubectl get pod unschedulable-pod -o yaml > pod.yaml
# 修改 pod.yaml: 删除 nodeName 字段,设置调度器为 ""
kubectl apply -f pod.yaml
# 查看调度器性能指标
kubectl get --raw /metrics | grep scheduler
Pod 是 Kubernetes 中的最小部署单元,它可以包含一个或多个容器。Pod 的生命周期包括从创建到删除的整个过程。理解 Pod 的生命周期,有助于我们更好地设计应用的启动、健康检查和优雅关闭机制。
Pod 阶段 (Phase):
# Pod 定义中包含初始化容器、探针和终止钩子
apiVersion: v1
kind: Pod
metadata:
name: my-pod
spec:
initContainers:
- name: init
image: busybox
command: ['sh', '-c', 'echo "Initializing..."']
containers:
- name: app
image: my-app:latest
ports:
- containerPort: 8080
startupProbe:
httpGet:
path: /health
port: 8080
initialDelaySeconds: 5
periodSeconds: 5
livenessProbe:
httpGet:
path: /health
port: 8080
periodSeconds: 10
readinessProbe:
httpGet:
path: /ready
port: 8080
lifecycle:
preStop:
exec:
command: ['sh', '-c', 'echo "Shutting down..."']
Pod 是易失性的——它们随时可能被重建、迁移、伸缩。直接使用 Pod 的 IP 地址作为服务入口是不可靠的。Kubernetes Service 提供了一种抽象,将一组 Pod 暴露为一个稳定的网络服务。CNI (Container Network Interface) 则定义了容器网络的标准接口,允许不同的网络插件替换实现。
Service 类型:
# 创建 ClusterIP Service
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
selector:
app: my-app
ports:
- port: 80
targetPort: 8080
# 查看 Service 端点
kubectl get endpoints my-service
# 查看 iptables 规则 (在节点上)
sudo iptables -t nat -L -n | grep my-service
# 使用 NodePort 暴露服务
apiVersion: v1
kind: Service
metadata:
name: my-nodeport
spec:
type: NodePort
selector:
app: my-app
ports:
- port: 80
targetPort: 8080
nodePort: 30080
Pod 是临时性的,它的存储会随着 Pod 的删除而消失。但对于数据库、消息队列等有状态应用,需要持久化存储。Kubernetes 通过 PV (PersistentVolume) 和 PVC (PersistentVolumeClaim) 实现存储的供应和消费分离。
持久卷 (PV): 集群中的存储资源,由管理员预先创建或通过 StorageClass 动态供应。
持久卷声明 (PVC): 用户对存储的请求,描述需要的大小、访问模式(ReadWriteOnce、ReadOnlyMany、ReadWriteMany)。
存储类 (StorageClass): 定义存储的类型、性能、回收策略等,用于动态供应 PV。
# 创建 StorageClass
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: fast-ssd
provisioner: kubernetes.io/no-provisioner
volumeBindingMode: WaitForFirstConsumer
# 创建 PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: my-pvc
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 5Gi
storageClassName: fast-ssd
# 在 Pod 中使用 PVC
apiVersion: v1
kind: Pod
metadata:
name: my-pod
spec:
containers:
- name: app
image: nginx
volumeMounts:
- name: my-storage
mountPath: /data
volumes:
- name: my-storage
persistentVolumeClaim:
claimName: my-pvc
Kubernetes 的核心设计哲学是声明式 (Declarative) 的。用户通过 YAML 文件描述期望状态(如 Deployment 的副本数、镜像版本),Kubernetes 控制器负责将实际状态调整为期望状态。控制器模式是 Kubernetes 实现自动化的基础。
控制器核心模式:
# 声明式创建资源 (推荐)
kubectl apply -f deployment.yaml
# 命令式更新 (不推荐)
kubectl scale deployment my-deploy --replicas=5
# 查看控制器状态
kubectl get deployment my-deploy -o yaml
# 查看控制器协调日志
kubectl logs -n kube-system kube-controller-manager-... -f
# 创建自定义控制器 (使用 Operator SDK)
operator-sdk create --domain mydomain --repo mydomain/my-operator
etcd 是一个分布式、高可用的键值存储,是 Kubernetes 的唯一状态存储。所有集群状态都保存在 etcd 中,包括 Pod、Service、ConfigMap 等资源对象。etcd 基于 Raft 共识算法 保证数据的一致性和高可用。
etcd 核心特性:
# 访问 etcd 容器 (在控制平面上)
kubectl exec -n kube-system etcd-master-... -- sh
# 查看 etcd 集群成员
etcdctl member list
# 查看所有键 (注意: Kubernetes 大量数据)
etcdctl get / --prefix
# 手动创建备份
etcdctl snapshot save /tmp/etcd-backup.db
# 从备份恢复
etcdctl snapshot restore /tmp/etcd-backup.db --data-dir /var/lib/etcd-restore
# 查看 etcd 状态
etcdctl endpoint status --write-out=table