目录

一、概念

1.1 概念

1.2 解决的核心问题

1.3 核心概念与对象

1.4 核心功能

1.5 功能边界

1.6 应用场景

二、架构与原理

2.1 核心架构

2.1.1 控制平面(Control Plane)- 大脑 / 管理员

2.1.2 工作节点(Worker Nodes)-劳动力 / 工人

2.2 一个简单的工作流程示例

三、使用

3.1 K8S安装

3.1.1 安装前的环境准备

3.1.2 使用 kubeadm 搭建集群

3.1.3 部署应用

3.2 托管 K8S 服务

3.3 YAML文件

3.4 简单的使用

3.5 常用命令

3.5.1 全局和集群管理命令

3.5.2 核心资源操作命令(增删改查)

3.5.3 Pod 故障排查和交互命令

3.5.4 特定资源常用命令

3.5.6 高级技巧和实用别名

3.6 Pod故障排查流程


一、概念

1.1 概念

Kubernetes(通常简称为 K8s)是一个开源的容器编排平台,用于自动化部署、扩展和管理容器化应用程序。

可以把它想象成一个数据中心的操作系统,或者一个集群的“大脑”。它负责管理成千上万个容器,确保它们按照你的意愿运行:该启动的时候启动,该扩容的时候扩容,出故障的时候能自动恢复。

1.2 解决的核心问题

在容器技术(如 Docker)普及之前,部署应用非常麻烦,环境依赖、资源冲突等问题层出不穷。容器解决了“环境一致性”的问题,但当需要运行成百上千个容器时,新的挑战出现了:

  • 如何管理这么多容器的生命周期? (启动、停止、重启)

  • 如何实现服务发现和负载均衡? (一个容器挂了,如何让流量转到其他健康的容器?)

  • 如何高效利用服务器资源? (如何把容器合理地调度到不同的机器上?)

  • 如何实现滚动更新和回滚? (发布新版本时如何做到不中断服务?)

  • 如何管理配置信息和敏感数据? (如密码、证书)

  • 如何实现应用的弹性伸缩? (根据 CPU 负载自动增加或减少容器数量)

Kubernetes 就是为了解决这些大规模容器管理问题而生的。

1.3 核心概念与对象

  • Pod

    • 最小部署单元:Pod 是 K8s 中最小的、可创建和管理的计算单位。

    • “一个逻辑主机”:一个 Pod 包含一个或多个紧密关联的容器(比如一个主应用容器和一个日志收集的 Sidecar 容器)。这些容器共享网络命名空间(同一个 IP 地址和端口空间)、存储卷和其他资源。

    • 同一个节点上的多个Pod有独立IP,并不是因为节点IP被细分了,而是Kubernetes利用Linux的网络命名空间技术,为每个Pod虚拟出了一个独立的网络环境,并从集群级别的IP地址池中为这个虚拟环境分配了一个全新的、全局唯一的IP地址。Pod 内的容器可以通过 localhost 互相通信。

    • 短暂存在:Pod 是短暂的,它们会被频繁地创建和销毁。每次创建一个新的 Pod,Kubernetes 都会从集群的 CIDR 地址池中动态地为它分配一个 IP 地址。因此,Pod 的 IP 不是固定的,不能直接依赖它来访问服务。

      • 当 Deployment 进行版本滚动更新时,会用新 Pod 替换旧 Pod。

      • 当 Pod 运行失败时,会被重启或重新调度到其他 Node。

      • 当集群缩容时,Pod 会被直接删除。

    • 一台虚拟机(节点)上可以有多个Pod,同一个节点的多个Pod共享该节点底层的物理资源,但这些Pod本身是相互隔离的。

  • Node(节点)

    • 集群中的工作机器,可以是物理机或虚拟机。

    • 每个 Node 上运行着 Kubelet(负责与主节点通信并管理 Pod)和容器运行时(如 Docker、containerd)。

  • Cluster(集群)

    • 由一组 Node(工作节点)和一个或多个 Master(控制平面)组成。

    • Master 是集群的“大脑”,包含 API Server、Scheduler、Controller Manager 等核心管理组件。它们负责接收用户指令、调度 Pod、维护集群状态等。

  • Service

    • 解决了一个关键问题:Pod 是短暂的,IP 地址会变,如何让前端应用稳定地找到后端应用?

    • Service 定义了一个稳定的访问入口(固定的 IP 地址和 DNS 名称),并将流量负载均衡到一组动态变化的 Pod 上。它是服务的抽象。

  • Deployment(控制器)

    • 最常用的控制器,定义Pod的期望状态,用于部署无状态应用(绝大多数Java微服务都是无状态的)。它管理ReplicaSet,从而控制Pod的副本数量、滚动更新和回滚。

    • 是一个通过 kubectl 提交给 API Server 的 API 对象(一种资源定义文件),它存在于 etcd(集群数据库)中。当交给Master后,由Master来控制集群行为。

    • 通过它可以轻松实现应用的蓝绿发布、金丝雀发布和版本回滚。

    • 应总是使用控制器来管理Pod,例如Deployment(用于无状态应用)、StatefulSet(用于有状态应用)、DaemonSetJob等。控制器能确保Pod的副本数始终符合预期,挂了一个会自动创建一个新的。

    • 它负责:

      • 部署和更新:实现无缝的滚动更新和回滚。

      • 扩缩容:轻松地增加或减少 Pod 的副本数量。

      • 自愈:如果某个 Pod 挂了,Deployment 会自动创建一个新的来替代它。

  • Namespace(命名空间)

    • 在物理集群内提供的虚拟隔离。可以将集群资源划分为不同的“区域”,用于实现多租户、环境隔离(如 dev, staging, prod)等。它隔离的是 API 对象(如 Pod、Service、Deployment)。

    • 不同 Namespace 的 Pod 可能运行在同一个 Node(虚拟机)上。它们共享 同一个 Node 的 CPU 和内存,但它们在 Kubernetes 内部是逻辑隔离的(默认情况下不能互相通过 Service 名访问,资源配额可以按 Namespace 限制等)。

    • 开发、测试、生产环境可以部署在同一个K8s集群的不同Namespace下,资源互不干扰。

  • ConfigMap 和 Secret

    • ConfigMap:用于将非机密的配置数据(如配置文件、环境变量)与容器镜像解耦。

    • Secret:类似于 ConfigMap,但专门用于存储敏感信息(如密码、OAuth 令牌、SSH 密钥),会以 base64 编码(注意:不是加密,需配合其他安全措施)。

1.4 核心功能

  • 服务发现与负载均衡

    • 通过 Service,K8s 可以自动为 Pod 集合提供一个唯一的 DNS 名称和虚拟 IP。流量会自动在健康的 Pod 实例间分发。

  • 存储编排

    • 可以自动挂载选择的存储系统(本地存储、公有云存储如 AWS EBS、GCP PD、网络文件系统如 NFS等)。

  • 自动部署与回滚

    • 可以描述应用的期望状态(通过 YAML/JSON 文件),K8s 会以可控的速度(如滚动更新)将实际状态变更至期望状态。如果出现问题,可以一键回滚到之前的版本。

  • 自动装箱(调度)

    • 根据每个 Pod 对 CPU、内存等资源的请求,K8s 调度器会智能地将其放置到合适的 Node 上运行,以最大化资源利用率。

  • 自我修复(自愈能力)

    • K8s 会不断检查 Pod 的健康状态。如果容器失败、节点宕机或健康检查不通过,它会自动重启容器、替换 Pod 或重新调度到健康节点,确保应用始终可用。

  • 密钥与配置管理

    • 使用 ConfigMap 和 Secret 管理部署配置和敏感信息,无需重新构建容器镜像,也无需在堆栈配置中暴露密钥。

  • 水平扩缩容

    • 可以根据 CPU 使用率或其他自定义指标,自动增加或减少 Pod 的副本数量(Horizontal Pod Autoscaler, HPA)。

    • 甚至可以基于更复杂的指标进行扩缩容(如 QPS - 每秒查询数)。

1.5 功能边界

  • 它不是 PaaS(平台即服务)

    • K8s 是一个平台的建设平台,而不是一个具体的应用平台。它提供了构建块(Primitives),而不是具体的解决方案。例如,它不提供数据库、消息队列、CI/CD 管道等“开箱即用”的服务,需要自己部署或集成。

  • 不限定支持的应用程序类型

    • K8s 支持各种工作负载,但它不关心运行的是无状态应用、有状态应用还是批处理任务。它只负责按照定义的规则去运行和管理它们。

  • 不提供中间件(如消息总线、数据库)

    • 需要自己部署和管理 MySQL、Redis、Kafka 等中间件,或者使用云服务商提供的托管服务并与 K8s 集成。

  • 不负责日志、监控和告警

    • K8s 本身提供了基础的监控指标(通过 Metrics Server),但企业级的日志收集、链路追踪、可视化监控面板(如 Grafana)和告警系统(如 Prometheus Alertmanager)需要自己搭建和集成。

  • 不提供 CI/CD 管道

    • 可以将 Jenkins、GitLab CI、Argo CD 等 CI/CD 工具与 K8s 集成,实现自动化部署,但 K8s 本身不包含这些功能。

  • 不解决所有网络安全问题

    • 虽然 K8s 提供了网络策略(Network Policies)来控制 Pod 之间的网络流量,但更复杂的安全策略(如 WAF - Web 应用防火墙)通常需要额外的工作。

1.6 应用场景

  • 微服务架构

    • 天然契合:微服务架构将应用拆分为多个小型、独立的服务。K8s 的 Service、Deployment、配置管理等功能,完美地解决了微服务的部署、发现、通信和治理问题。

  • 传统应用现代化(迁移上云)

    • 将传统的单体应用进行容器化改造,并部署到 K8s 上,可以立即获得弹性伸缩、高可用和敏捷部署等云原生能力。

  • 混合云与多云部署

    • K8s 提供了跨不同云服务商(AWS, Azure, GCP)或混合云(本地数据中心+公有云)的一致性的部署和管理体验,避免被单一云厂商锁定。

  • 部署复杂的有状态应用

    • 早期 K8s 主要针对无状态应用,但现在通过 StatefulSetPersistent Volumes 等对象,可以稳定地运行数据库(如 MySQL集群)、缓存系统(如 Redis集群)、大数据框架(如 Spark)等有状态应用。

  • 批处理任务和机器学习

    • 使用 Job 和 CronJob 控制器,可以方便地运行一次性任务或定时任务,例如数据备份、报表生成、模型训练等。

  • 高流量、需要快速弹性伸缩的网站/API

    • 例如电商网站在大促期间,可以利用 K8s 的 HPA 功能,根据流量自动扩容,平稳度过高峰,并在高峰过后自动缩容以节省成本。

不需要Kubernetes的场景:

  • 团队规模小,应用非常简单:如果你的应用只是一个简单的单体应用,且流量稳定,使用 K8s 会引入不必要的复杂性。直接使用虚拟机或简单的 PaaS(如 Heroku)可能更高效。

  • 缺乏运维经验和专业知识:K8s 的学习曲线陡峭,管理和维护一个生产级 K8s 集群需要深厚的知识。此时可以考虑使用托管K8s服务(如 GKE, EKS, AKS),将控制平面的管理负担交给云厂商。

  • 对资源极其敏感:K8s 集群本身(控制平面和工作节点上的组件)会消耗一定的计算资源。对于资源极其受限的边缘场景,可能更轻量级的方案(如 K3s)更合适。

二、架构与原理

2.1 核心架构

Kubernetes 遵循经典的客户端-服务器架构。一个 Kubernetes 集群由一组机器(物理机或虚拟机)组成,这些机器被分为两种角色:

2.1.1 控制平面(Control Plane)- 大脑 / 管理员

控制平面是集群的“指挥中心”,负责管理集群的所有决策。它通常包含以下核心组件:

  • kube-apiserver集群的网关和总控台。所有与集群的通信(无论是来自内部组件还是外部用户命令 kubectl)都必须通过 API Server。它是唯一与 etcd 直接交互的组件。负责请求的认证、授权和准入控制。API Server 是无状态的,其状态数据存储在 etcd 中。为了高可用,可以部署多个 API Server 实例进行负载均衡。

  • etcd集群的“记忆库”。一个高可用、强一致性的分布式键值数据库,持久化存储了整个集群的所有配置数据和工作状态(例如,有哪些 Pod、运行在哪个节点上等)。它是 Kubernetes 的“唯一信源”。它是 Kubernetes 集群的唯一有状态的核心组件,其数据的安全性和高可用性至关重要。通常需要为其配置备份和高可用方案。

  • kube-scheduler调度中心。它负责监听 API Server,,发现新建的、还未被分配到任何节点的 Pod(其 nodeName 为空),并根据资源需求、策略等因素,选择一个最合适的 Node 来运行它。Scheduler 只做决策,不执行。它通过 API Server 将决策(更新 Pod 的 nodeName 字段)写入 etcd。

  • kube-controller-manager控制器管家。它内部运行着多种控制器(Controller),每个控制器都是一个独立的控制循环,负责监控集群的状态并确保其与期望状态一致。

    • 节点控制器(Node Controller):负责节点宕机后的通知和响应。

    • 副本控制器(Replication Controller):确保 Pod 的副本数量始终与期望值一致(例如,Deployment 的控制器)。

    • 端点控制器:为 Service 填充 Endpoint 对象(即 Pod IP:Port)。

    • 服务账户和令牌控制器:为新的命名空间创建默认账户和 API 访问令牌。

  • cloud-controller-manager云平台联络员。用于与底层云提供商(如 AWS、GCP、Azure)的 API 交互,管理负载均衡器、存储卷等云资源。

2.1.2 工作节点(Worker Nodes)-劳动力 / 工人

工作节点是真正运行应用程序容器的地方。每个节点上都必须运行以下组件:

  • kubelet节点代理。它是控制平面在该节点上的“代表”,负责与 API Server 通信,管理本节点上 Pod 的生命周期(如创建、销毁 Pod),并确保容器健康运行。定期向 API Server 汇报节点和 Pod 的状态(如 CPU/内存使用情况)。kubelet 不管理非 Kubernetes 创建的容器。

  • kube-proxy网络代理。它负责维护节点上的网络规则,实现 Kubernetes Service 的概念,如负载均衡和将流量转发到正确的 Pod。实现方式可以是 iptables(默认)或 ipvs(性能更好)。

  • 容器运行时(Container Runtime)容器引擎。是真正负责下载容器镜像、启动和停止容器的组件,最常见的是 Docker、containerd、CRI-O 等。Kubernetes 通过 容器运行时接口 支持多种运行时,如 containerd(目前最主流)、CRI-O 等。早期直接使用 Docker,但现在通过 CRI 与容器运行时交互,Docker 本身已被 containerd 取代。

2.2 一个简单的工作流程示例

假设要部署一个包含 3 个副本的 Nginx 应用:

  1. 定义 YAML 文件:编写一个 deployment.yaml 文件,描述期望状态:使用 Nginx 镜像,创建 3 个副本。

  2. kubectl 提交 YAML:使用 kubectl apply -f deployment.yaml 命令将文件提交给 kube-apiserver

  3. API Server 持久化kube-apiserver 对请求进行认证和验证,然后将期望状态写入 etcd

  4. Deployment 控制器检测到变化:Deployment 控制器通过 Watch 机制发现了新的 Deployment 对象。它意识到需要创建对应的 ReplicaSet。

  5. ReplicaSet 控制器开始工作:ReplicaSet 控制器发现新的 ReplicaSet,并意识到当前 Pod 数量(0)与期望数量(3)不符。它通过 API Server 创建 3 个 Pod 定义(此时 Pod 还没有被调度)。

  6. 调度器发现待调度的 Pod:调度器kube-scheduler发现这 3 个新的 Pod 的 nodeName 为空。它开始执行调度流程:

    1. 预选:过滤掉所有不健康的、资源不足的节点。

    2. 优选:对剩余节点打分,选出最优的 3 个节点(可能分散在不同节点上)。

  7. 调度器绑定:调度器kube-scheduler将 Pod 与节点绑定的信息(更新 Pod 的 nodeName 字段)通过 kube-apiserver 写入 etcd。

  8. 目标节点上的 kubelet 被唤醒:各个被选中的节点上的 kubelet 通过 Watch 机制发现有一个 Pod 被调度到了自己这里。

  9. kubelet 创建 Pod

    1. kubelet 通过容器运行时接口调用本地的容器运行时(如 containerd)。

    2. 容器运行时从镜像仓库拉取 Nginx 镜像。

    3. 创建并启动容器。

  10. kubelet 上报状态:kubelet 持续监控容器状态,并通过 API Server 将 Pod 的状态(如 Running)更新回 etcd。kubelet 会持续向控制平面报告 Pod 的状态。如果有一个 Pod 崩溃,Replication Controller(由 kube-controller-manager 管理)会检测到实际状态与期望状态(3个副本)不符,于是它会创建新的 Pod 来替代。

  11. kube-proxy 更新网络规则:在整个过程中,如果创建了 Service,kube-proxy 会监听到 Service 和 Endpoint 的变化,并在本机更新 iptables/ipvs 规则,以便将服务流量负载均衡到新创建的 Pod。

  12. 提供服务:你创建一个 Service,它通过标签找到这 3 个 Nginx Pod,并提供统一的访问入口。

三、使用

3.1 K8S安装

3.1.1 安装前的环境准备

  • 服务器:至少准备两台(一台Master,一台Node)Linux机器。虚拟机或物理机均可。

  • 操作系统:推荐使用 Ubuntu 16.04/18.04/20.04 或 CentOS 7/8 等稳定版本。

  • 硬件配置:每个节点建议至少 2核CPU 和 2GB内存

  • 网络:确保所有节点之间网络互通。

在系统层面,需要完成以下配置:

  • 关闭 Swap:Kubernetes 要求必须禁用交换分区(Swap)。
swapoff -a  # 临时关闭
sed -i '/swap/s/^/#/' /etc/fstab  # 永久关闭,注释掉swap行
  • 配置主机名与解析:为每个节点设置唯一的主机名,并确保 /etc/hosts 文件包含所有节点的IP和主机名映射。

  • 时间同步:确保所有节点时间准确,安装并启用NTP服务。

  • 开放防火墙端口:根据你选择的网络插件等,需要在防火墙中放行必要的端口。以下是一些核心端口:

组件/协议端口说明
API Server6443/TCP所有组件通信的入口
etcd2379-2380/TCP数据库客户端API(如果etcd部署在控制平面节点上)
Kubelet API10250/TCP节点上与Kubelet通信的端口
NodePort Services30000-32767/TCP对外暴露服务的外部端口范围

3.1.2 使用 kubeadm 搭建集群

步骤 1: 安装容器运行时(所有节点)

Kubernetes 需要容器运行时来管理容器。以安装 Docker 为例:

# 更新软件包索引
sudo apt-get update
# 安装Docker
sudo apt-get install -y docker.io
# 设置开机自启并启动Docker服务
sudo systemctl enable docker
sudo systemctl start docker

步骤 2: 安装 kubeadm、kubelet、kubectl(所有节点)

添加 Kubernetes 软件源:由于网络原因,在国内环境下建议使用国内镜像源,例如阿里云。

# 更新apt包索引并安装依赖
sudo apt-get update && sudo apt-get install -y apt-transport-https curl
# 添加Kubernetes的GPG密钥
curl -s https://mirrors.aliyun.com/kubernetes/apt/doc/apt-key.gpg | sudo apt-key add -
# 添加阿里云的Kubernetes软件源
cat <<EOF | sudo tee /etc/apt/sources.list.d/kubernetes.list
deb https://mirrors.aliyun.com/kubernetes/apt/ kubernetes-xenial main
EOF
sudo apt-get update

安装核心组件:

sudo apt-get install -y kubelet kubeadm kubectl
# 阻止这三个包被自动升级,避免版本不兼容
sudo apt-mark hold kubelet kubeadm kubectl

步骤 3: 初始化控制平面(Master节点)

在主节点上执行初始化命令:

# --pod-network-cidr 需要与你将要安装的网络插件匹配
sudo kubeadm init --pod-network-cidr=10.244.0.0/16

重要! 初始化成功后会输出一行 kubeadm join 命令,请务必复制保存,后续加入工作节点时需要用到。

步骤 4: 配置 kubectl(Master节点)

让当前用户能够使用 kubectl 管理集群。

mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config

步骤 5: 安装 Pod 网络插件(Master节点)

没有网络插件,Pod 之间无法通信。这里以 Flannel 为例。

kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml

步骤 6: 加入工作节点(Node节点)

在每个工作节点上,执行步骤3中保存的 kubeadm join 命令。

sudo kubeadm join <Master节点的IP>:6443 --token <token> --discovery-token-ca-cert-hash sha256:<hash>

步骤 7: 验证集群状态(Master节点)

在所有节点加入后,在Master节点执行以下命令检查集群状态。

# 查看所有节点状态,确认状态都是 Ready
kubectl get nodes

3.1.3 部署应用

集群运行起来后,可以快速部署一个测试应用(如Nginx)来验证一切正常。

# 创建一个Deployment来运行Nginx容器
kubectl create deployment nginx --image=nginx:1.18
# 创建一个Service将Nginx暴露到集群外(通过NodePort方式)
kubectl expose deployment nginx --type=NodePort --port=80 --target-port=80 --name=nginx-service
# 查看服务详情,获取外部访问的端口
kubectl get svc nginx-service

之后,就可以通过任意节点的IP地址和分配的端口(如 http://<节点IP>:31000)在浏览器中访问这个Nginx服务了。

3.2 托管 K8S 服务

对于生产环境,强烈推荐使用云厂商的托管服务,它们负责管理控制平面,你只需关心工作节点。

  • Google GKE (Google Kubernetes Engine)

  • Amazon EKS (Elastic Kubernetes Service)

  • Microsoft AKS (Azure Kubernetes Service)

  • 阿里云 ACK (Container Service for Kubernetes)

只需在云控制台点击几下,或使用 CLI 工具,即可创建一个高可用的生产级集群。

3.3 YAML文件

Kubernetes (K8S) 的 YAML 文件是定义和配置 Kubernetes 资源的核心。

Kubernetes 的 YAML 文件主要包含以下四个顶层(根级)字段,它们是几乎所有资源的基石:

  • apiVersion: 指定使用的 Kubernetes API 的版本。不同的资源对象存在于不同的 API 组中。

    • 核心组(如 Pod、Service、Namespace): v1

    • Apps 组(如 Deployment、StatefulSet): apps/v1

    • 批处理组(如 Job): batch/v1

    • 扩展组(如 Ingress): networking.k8s.io/v1

  • kind: 定义要创建的资源类型。例如: PodServiceDeploymentConfigMapSecret 等。

  • metadata: 存放资源的元数据,用于标识和描述资源。

    • name: 资源的名称,在同一个命名空间内必须唯一。

    • namespace: (可选) 资源所属的命名空间。不指定则默认为 default

    • labels: (可选) 键值对标签,用于标识、选择和分组资源。非常灵活和重要。

    • annotations: (可选) 键值对注释,用于存储非识别性的元数据,供工具或库使用(如版本信息、构建信息等)。

  • spec: 这是文件的核心,意为“规约”或“期望状态”。你在这里详细描述你希望资源达到什么样的状态。例如,对于 Pod,你会在这里定义它包含哪些容器、使用什么镜像等。每个资源类型的 spec 结构都完全不同。

  • status: (自动生成) 描述了资源的实际状态。这个字段是由 Kubernetes 系统自动填充和更新的,你永远不需要在创建的 YAML 文件中定义它。它反映了资源当前的健康状况、IP 地址等信息。

常用资源spec字段详解:

Pod (kind: Pod) 的 spec

  • Pod: 最小的可部署计算单元,通常容纳一个或多个容器。

字段子字段数据类型是否必填详细解说与示例
containers-List<Object>定义 Pod 中运行的容器列表。
containers[].nameString容器的名称。示例: nginx-container
containers[].imageString容器镜像地址。示例: nginx:1.20.1
containers[].portsList<Object>容器暴露的端口列表(主要是声明性作用,不影响网络)。
containers[].ports[].containerPortInteger容器内监听的端口号。示例: 80
containers[].envList<Object>传递给容器的环境变量列表。
containers[].env[].nameString环境变量名称。示例: DB_HOST
containers[].env[].valueString环境变量的值。示例: mysql-service
containers[].resourcesObject推荐容器资源请求和限制,对集群稳定性至关重要
resources.requestsObject容器启动所需的最小资源量(调度依据)。示例: memory: "64Mi"cpu: "250m"
resources.limitsObject容器所能使用的最大资源量。示例: memory: "128Mi"cpu: "500m"

Deployment (kind: DeploymentapiVersion: apps/v1) 的 spec

  • Deployment: 管理 Pod 副本和更新的控制器。

字段子字段数据类型是否必填详细解说与示例
replicas-Integer期望的 Pod 副本数量,默认为 1。示例: 3
selector-Object标签选择器,Deployment 通过它来识别要管理的 Pod。
selector.matchLabelsMap<String, String>必须与下面 template 中定义的 Pod 标签匹配。示例: app: my-app
template-Object用于创建新 Pod 的模板。其下就是 Pod 的 metadata 和 spec
template.metadataObjectPod 的元数据,必须包含 selector 中指定的标签
template.specObjectPod 的规约,与上述 Pod 的 spec 结构完全一致。

Service (kind: Service) 的 spec

  • Service: 为一组 Pod 提供稳定的网络访问入口。

字段子字段数据类型是否必填详细解说与示例
type-StringService 的类型。可选值: ClusterIP (默认,集群内访问), NodePort (通过节点IP访问), LoadBalancer (云平台负载均衡器)
selector-Map<String, String> (对于 ClusterIP/NodePort)标签选择器,Service 通过它来发现并代理后端的 Pod。示例: app: my-app
ports-List<Object>端口映射规则列表。
ports[].portIntegerService 自身暴露的端口。示例: 80
ports[].targetPortInteger/String后端 Pod 容器的端口(对应 containerPort),默认与 port 相同。示例: 80 或 http
ports[].nodePortInteger当 type=NodePort 时,节点上映射的端口(30000-32767)。

3.4 简单的使用

举例:在K8S中部署3台Nginx和2台SpringBoot服务

1、部署SpringBoot服务

SpringBoot Deployment配置

# springboot-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: springboot-app
  labels:
    app: springboot-app
spec:
  replicas: 2
  selector:
    matchLabels:
      app: springboot-app
  template:
    metadata:
      labels:
        app: springboot-app
    spec:
      containers:
      - name: springboot-app
        image: your-springboot-image:latest  # 替换为您的镜像
        ports:
        - containerPort: 8080
        env:
        - name: SPRING_PROFILES_ACTIVE
          value: "prod"
        resources:
          requests:
            memory: "512Mi"
            cpu: "250m"
          limits:
            memory: "1Gi"
            cpu: "500m"

SpringBoot Service配置

# springboot-service.yaml
apiVersion: v1
kind: Service
metadata:
  name: springboot-service
spec:
  selector:
    app: springboot-app
  ports:
    - protocol: TCP
      port: 80
      targetPort: 8080
  type: ClusterIP

2、部署Nginx服务

Nginx ConfigMap配置(包含反向代理配置)

# nginx-configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: nginx-config
data:
  nginx.conf: |
    events {
        worker_connections 1024;
    }
    
    http {
        upstream springboot_backend {
            server springboot-service:80;
        }
        
        server {
            listen 80;
            
            location / {
                proxy_pass http://springboot_backend;
                proxy_set_header Host $host;
                proxy_set_header X-Real-IP $remote_addr;
                proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
                proxy_set_header X-Forwarded-Proto $scheme;
            }
            
            # 健康检查
            location /health {
                access_log off;
                return 200 "healthy\n";
                add_header Content-Type text/plain;
            }
        }
    }

Nginx Deployment配置

# nginx-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
  labels:
    app: nginx
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1.25
        ports:
        - containerPort: 80
        volumeMounts:
        - name: nginx-config
          mountPath: /etc/nginx/nginx.conf
          subPath: nginx.conf
        livenessProbe:
          httpGet:
            path: /health
            port: 80
          initialDelaySeconds: 30
          periodSeconds: 10
        readinessProbe:
          httpGet:
            path: /health
            port: 80
          initialDelaySeconds: 5
          periodSeconds: 5
        resources:
          requests:
            memory: "128Mi"
            cpu: "100m"
          limits:
            memory: "256Mi"
            cpu: "200m"
      volumes:
      - name: nginx-config
        configMap:
          name: nginx-config
          items:
          - key: nginx.conf
            path: nginx.conf

Nginx Service配置(对外暴露)

# nginx-service.yaml
apiVersion: v1
kind: Service
metadata:
  name: nginx-service
spec:
  selector:
    app: nginx
  ports:
    - protocol: TCP
      port: 80
      targetPort: 80
  type: LoadBalancer  # 或者使用NodePort根据您的环境选择

部署命令

# 应用所有配置
kubectl apply -f .

# 或者分别部署
kubectl apply -f springboot-deployment.yaml
kubectl apply -f springboot-service.yaml
kubectl apply -f nginx-configmap.yaml
kubectl apply -f nginx-deployment.yaml
kubectl apply -f nginx-service.yaml

验证部署

# 检查Pod状态
kubectl get pods -o wide

# 检查Service
kubectl get services

# 检查Deployment
kubectl get deployments

# 查看Pod日志
kubectl logs -l app=springboot-app --tail=50
kubectl logs -l app=nginx --tail=50

# 测试服务连通性
kubectl exec -it <nginx-pod> -- curl http://springboot-service/health

扩展配置(可选)

# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: app-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - host: your-domain.com  # 替换为您的域名
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: nginx-service
            port:
              number: 80

3.5 常用命令

3.5.1 全局和集群管理命令

这些命令用于查看集群状态和配置。

命令作用示例
kubectl version查看客户端和服务器端的 Kubernetes 版本kubectl version --short (简洁显示)
kubectl cluster-info显示集群主节点和核心服务的地址kubectl cluster-info
kubectl config current-context显示当前使用的上下文(环境)kubectl config current-context
kubectl config get-contexts列出所有可用的上下文kubectl config get-contexts
kubectl config use-context <context-name>切换到指定的上下文(如从开发切换到生产)kubectl config use-context prod-cluster
kubectl get nodes查看集群中所有节点的状态

3.5.2 核心资源操作命令(增删改查)

这是最常用的一组命令,适用于几乎所有资源类型(Pod, Deployment, Service 等)。其通用语法是 kubectl <动作> <资源类型> [资源名称]

a) 查询和查看(Get & Describe)

命令作用示例和常用参数
kubectl get列出资源。最基本、最常用的命令。kubectl get pods
kubectl get deployments
kubectl get services 或 kubectl get svc
kubectl get all (列出所有常见资源)
常用参数-n <namespace>: 指定命名空间
-o wide: 显示更详细信息(如IP,节点)
-o yaml 或 -o json: 以YAML/JSON格式输出
--watch 或 -w: 实时监听资源变化
kubectl get pods -n kube-system
kubectl get pod my-pod -o yaml
kubectl describe详细描述某个资源的状态、事件、配置等。用于排障kubectl describe pod <pod-name>
kubectl describe deployment/<deployment-name>
kubectl explain查看某个资源的字段说明,写YAML时的好帮手。kubectl explain pod.spec.containers

b) 创建和删除(Create & Delete)

命令作用示例
kubectl create命令式创建资源。通常通过 YAML 文件。kubectl create -f my-deployment.yaml
kubectl apply声明式创建或更新资源。推荐使用此命令,因为它可以幂等地应用配置。kubectl apply -f my-deployment.yaml
kubectl delete删除资源。kubectl delete -f my-deployment.yaml (通过文件删除)
kubectl delete pod <pod-name> (直接删除指定资源)
kubectl delete deployment <deployment-name> --force --grace-period=0 (强制立即删除)

c) 编辑和更新(Edit & Patch)

命令作用示例
kubectl edit直接编辑集群中的现有资源配置。会打开默认编辑器(如vim)。kubectl edit deployment/<deployment-name>
kubectl patch对资源进行局部更新,无需编辑整个文件。kubectl patch deployment my-deployment -p '{"spec":{"replicas": 3}}'
kubectl scale伸缩 Pod 副本数量。kubectl scale deployment/<deployment-name> --replicas=5
kubectl set image更新 Deployment 的容器镜像,触发滚动更新。kubectl set image deployment/<deployment-name> nginx=nginx:1.19

3.5.3 Pod 故障排查和交互命令

当 Pod 出现问题时,这些命令至关重要。

命令作用示例和常用参数
kubectl logs查看 Pod 中容器的日志。kubectl logs <pod-name>
kubectl logs -f <pod-name> (实时追踪日志,类似 tail -f
kubectl logs <pod-name> -c <container-name> (Pod内含多个容器时指定)
kubectl exec在 Pod 的容器中执行命令。用于交互式调试。kubectl exec -it <pod-name> -- /bin/bash (进入容器的shell)
kubectl exec <pod-name> -- ls /app (执行单条命令)
kubectl port-forward将本地端口转发到 Pod 的端口。用于临时访问集群内部服务。kubectl port-forward <pod-name> 8080:80 (将本地8080转发到Pod的80端口)
kubectl port-forward service/<svc-name> 8080:80 (转发到Service)
kubectl cp在本地和 Pod 容器之间复制文件。kubectl cp /local/file <pod-name>:/path/in/pod
kubectl cp <pod-name>:/path/to/file /local/dest

3.5.4 特定资源常用命令

资源类型常用命令说明
Deploymentkubectl rollout status deployment/<name>查看滚动更新的状态
kubectl rollout history deployment/<name>查看更新历史
kubectl rollout undo deployment/<name>回滚到上一个版本
kubectl rollout undo deployment/<name> --to-revision=2回滚到指定版本
ConfigMap/Secretkubectl get configmap查看ConfigMap
kubectl create secret generic my-secret --from-literal=key=value命令式创建Secret

3.5.6 高级技巧和实用别名

  • 使用别名提高效率

        将 kubectl 别名设置为 k,并设置一些常用资源的别名。

alias k=kubectl
alias kgp='k get pods'
alias kgd='k get deployments'
alias kdp='k describe pod'

        在 ~/.bashrc 或 ~/.zshrc 中配置使其永久生效。

  • 动态补全(Auto Completion)

    启用 kubectl 的自动补全功能,可以大幅提高输入准确性和速度。

    Bash: source <(kubectl completion bash)

    Zsh: source <(kubectl completion zsh)

  • --dry-run=client -o yaml

    这是一个非常有用的技巧,可以生成一个基础的 YAML 模板,而无需真正创建资源。然后可以基于这个模板进行修改。

kubectl create deployment my-nginx --image=nginx --dry-run=client -o yaml > deployment.yaml

3.6 Pod故障排查流程

假设一个 Pod 无法正常运行,一个典型的排查流程是:

  1. 查看状态kubectl get pods -o wide (看Pod是否Running,在哪个节点)

  2. 查看详情kubectl describe pod <problem-pod-name> (查看Events部分,常有错误原因)

  3. 查看日志kubectl logs <problem-pod-name> (查看应用本身的错误输出)

  4. 进入Pod:如果日志不清,尝试 kubectl exec -it <problem-pod-name> -- /bin/sh 进入容器内部检查。

  5. 端口转发测试kubectl port-forward <problem-pod-name> 8080:80,然后在本地用 curl localhost:8080 测试服务是否正常。

Logo

码道开发者社区,聚焦华为云码道 CodeArts 代码智能体,沉淀 Agent、Skill、鸿蒙开发实战内容,供开发者查阅资料、交流技术、分享工程实践

更多推荐