spinny:~/writing $ vim introduction-to-kubernetes.md
1~2如果您在软件开发领域工作,您肯定听说过 Kubernetes。但它到底是什么,为什么它已成为管理容器化应用程序的事实标准?本指南将带您从基础知识到核心概念,并提供实际示例和图表以帮助您理解。3~4## Kubernetes 之前:简要历史5~6要理解为什么 Kubernetes 如此具有革命性,让我们先回顾一下。7~81. **传统部署**:最初,应用程序在物理服务器上运行。这种方法成本高昂,难以扩展,且容易出现资源冲突。92. **虚拟化部署**:然后出现了虚拟机(VM)。VM 允许在同一硬件上运行多个隔离的应用程序,从而提高了资源利用率和安全性。然而,每个 VM 都运行一个完整的操作系统,消耗大量资源。103. **容器化部署**:容器(如 Docker)是下一个演进。它们共享相同的主机操作系统,但运行隔离的进程。它们轻量、启动快且可移植。11~12容器解决了可移植性问题,但又带来了另一个问题:如何在生产环境中管理成百上千个容器?如何确保它们始终在运行,能够相互通信,并根据负载进行扩展?13~14**Kubernetes** 正是为此而生。15~16## 什么是 Kubernetes?17~18Kubernetes(通常缩写为 **K8s**)是一个用于容器编排的开源平台。简单来说,它自动化了容器化应用程序的部署、扩展和管理。由 Google 创建,现在由云原生计算基金会(CNCF)维护,Kubernetes 已成为任何大规模使用微服务的人的首选工具。19~20## Kubernetes 集群的架构21~22Kubernetes 环境被称为**集群**。集群由一组称为**节点**的计算机组成,这些节点运行我们的应用程序。该架构分为两个主要部分:控制平面和工作节点。23~24```mermaid25graph TD26 subgraph "控制平面 (Master)"27 A["API 服务器"]28 B["etcd"]29 C["调度器"]30 D["控制器管理器"]31 end32~33 subgraph "工作节点 1"34 E["Kubelet"] --- F["容器运行时"]35 G["Kube-proxy"]36 F --- H["Pod"]37 F --- I["Pod"]38 end39~40 subgraph "工作节点 2"41 J["Kubelet"] --- K["容器运行时"]42 L["Kube-proxy"]43 K --- M["Pod"]44 end45~46 A -- "通信" --> E47 A -- "通信" --> J48 User -- "kubectl" --> A49 C -- "将 Pod 分配给节点" --> E50 D -- "维护状态" --> A51 A -- "保存/读取状态" --> B52```53~54### 控制平面55~56控制平面是集群的“大脑”。它做出全局决策(如调度),并检测和响应集群事件。其主要组件包括:57~58- **API 服务器 (`kube-apiserver`)**:它是集群的网关。它暴露了 Kubernetes API,用户(通过 `kubectl`)、集群组件和外部工具都使用它进行通信。59- **etcd**:一个一致且高可用的键值数据库。它存储所有集群数据,代表了系统的期望状态和当前状态。60- **调度器 (`kube-scheduler`)**:将新创建的 Pod 分配给可用的工作节点,同时考虑资源需求、策略和其他约束。61- **控制器管理器 (`kube-controller-manager`)**:运行控制器,这些控制器是监视集群状态并努力使其达到期望状态的控制循环。例如,`Node Controller` 管理节点,而 `Replication Controller` 确保运行正确数量的 Pod。62~63### 工作节点64~65工作节点是实际运行应用程序的机器(物理或虚拟)。每个节点都由控制平面管理,并包含以下组件:66~67- **Kubelet**:在每个节点上运行的代理。它确保 Pod 中描述的容器正在运行且健康。68- **Kube-proxy**:一个网络代理,用于管理节点上的网络规则。它允许从集群内部或外部的网络会话与 Pod 进行网络通信。69- **容器运行时**:负责运行容器的软件。Docker 是最著名的,但 Kubernetes 也支持其他运行时,如 `containerd` 和 `CRI-O`。70~71## 基本的 Kubernetes 对象72~73在 Kubernetes 中,一切都由**对象**表示。这些对象是“意图记录”:一旦创建了一个对象,Kubernetes 就会不断努力确保它存在并与期望状态匹配。74~75以下是最重要的几个:76~77### Pod78~79**Pod** 是 Kubernetes 中最小的执行单元。它代表一个或多个在同一节点上一起运行的容器,共享网络和存储等资源。80~81通常,每个 Pod 只运行一个容器,但在高级场景中(如用于日志记录或监控的“sidecar 容器”),可以有多个。82~83您几乎从不直接创建 Pod。您会使用更高级别的抽象,如 Deployment。84~85### Deployment86~87**Deployment** 是您最常使用的对象。它描述了一组相同 Pod 的期望状态。Deployment 控制器负责:88~89- 创建和管理一个 **ReplicaSet**(另一个对象,确保始终运行特定数量的 Pod 副本)。90- **扩展** Pod 的数量(增加或减少)。91- 以受控方式管理应用程序**更新**(例如,*滚动更新*),而不会停机。92~93这是一个运行 3 个 NGINX 服务器副本的 Deployment 的 YAML 文件示例:94~95```yaml96# nginx-deployment.yaml97apiVersion: apps/v198kind: Deployment99metadata:100 name: nginx-deployment101spec:102 replicas: 3103 selector:104 matchLabels:105 app: nginx106 template:107 metadata:108 labels:109 app: nginx110 spec:111 containers:112 - name: nginx113 image: nginx:1.14.2114 ports:115 - containerPort: 80116```117~118### Service119~120Kubernetes 中的 Pod 是短暂的:它们可以随时被创建和销毁。每个 Pod 都有自己的 IP 地址,但这个 IP 地址并不稳定。那么,我们如何可靠地暴露我们的应用程序呢?121~122通过 **Service**。Service 是一个抽象,它定义了一组逻辑上的 Pod 和访问它们的策略。它为一组 Pod 提供了一个**稳定的接入点**(一个虚拟 IP 地址和一个 DNS 名称)。123~124```mermaid125graph TD126 subgraph "Service (nginx-service)"127 A["ClusterIP: 10.96.0.10"]128 end129~130 subgraph "Pods"131 B("Pod 1 - IP: 192.168.1.2")132 C("Pod 2 - IP: 192.168.1.3")133 D("Pod 3 - IP: 192.168.1.4")134 end135~136 A -- "Selector: app=nginx" --> B137 A -- "Selector: app=nginx" --> C138 A -- "Selector: app=nginx" --> D139~140 Client -- "请求 nginx-service" --> A141```142~143Service 使用基于`标签`的 `selector` 来查找应将流量转发到的 Pod。144~145以下是如何为我们的 NGINX Deployment 创建一个 Service:146~147```yaml148# nginx-service.yaml149apiVersion: v1150kind: Service151metadata:152 name: nginx-service153spec:154 selector:155 app: nginx156 ports:157 - protocol: TCP158 port: 80159 targetPort: 80160 type: ClusterIP # 默认 - 仅在集群内部暴露服务161```162~163有不同类型的 Service:164- `ClusterIP`:在集群内部 IP 上暴露服务(默认)。165- `NodePort`:在每个工作节点的静态端口上暴露服务。166- `LoadBalancer`:在云提供商(如 AWS、GCP)中创建一个外部负载均衡器,并为服务分配一个公共 IP。167~168### Ingress169~170`LoadBalancer` 类型的 Service 很棒,但为每个服务都创建一个可能成本高昂。要向外部世界暴露多个 HTTP/HTTPS 服务,您可以使用 **Ingress**。171~172Ingress 充当外部流量的“智能路由器”。它允许您根据主机(例如 `api.mysite.com`)或路径(例如 `mysite.com/api`)定义路由规则。173~174```mermaid175graph LR176 User -- "mysite.com/api" --> Ingress177 User -- "mysite.com/ui" --> Ingress178~179 subgraph "Cluster"180 Ingress -- "/api" --> ServiceA("api-service")181 Ingress -- "/ui" --> ServiceB("ui-service")182~183 ServiceA --> PodA1("API Pod 1")184 ServiceA --> PodA2("API Pod 2")185~186 ServiceB --> PodB1("UI Pod 1")187 ServiceB --> PodB2("UI Pod 2")188 end189```190~191以下是一个 Ingress 的示例:192```yaml193# example-ingress.yaml194apiVersion: networking.k8s.io/v1195kind: Ingress196metadata:197 name: example-ingress198spec:199 rules:200 - host: mysite.com201 http:202 paths:203 - path: /api204 pathType: Prefix205 backend:206 service:207 name: api-service208 port:209 number: 8080210 - path: /ui211 pathType: Prefix212 backend:213 service:214 name: ui-service215 port:216 number: 3000217```218~219### 其他有用的对象220~221- **Namespace**:允许您在物理集群内创建“虚拟集群”。用于隔离环境(例如 `development`、`staging`、`production`)或团队。222- **ConfigMap 和 Secret**:用于管理与容器镜像分离的配置数据和机密(如密码或 API 密钥)。223- **StatefulSet**:类似于 Deployment,但专门用于需要稳定网络标识和持久存储的有状态应用程序(如数据库)。224- **PersistentVolume (PV) 和 PersistentVolumeClaim (PVC)**:用于管理集群中的持久存储。225~226## 结论227~228Kubernetes 是一个非常强大的工具,但其学习曲线可能很陡峭。本指南只是浅尝辄止,但我们希望它能让您对基本概念有一个扎实的理解。229~230**接下来做什么?**231- **在本地进行实验**:安装 [Minikube](https://minikube.sigs.k8s.io/docs/start/) 或 [Kind](https://kind.sigs.k8s.io/docs/user/quick-start/) 在您的计算机上创建一个 Kubernetes 集群。232- **使用 `kubectl`**:熟悉 `kubectl` 命令,这是您与集群交互的主要工具。尝试创建本文中的 NGINX Deployment 和 Service。233- **探索官方教程**:[Kubernetes 文档](https://kubernetes.io/docs/tutorials/) 是一个充满示例的绝佳资源。234~235容器编排是云原生世界中的一项基本技能,掌握 Kubernetes 将为您打开一个充满可能性的世界。玩得开心!
NORMAL · introduction-to-kubernetes.md [readonly]235 lines · :q to close