本教程介绍如何使用负载平衡器在外部 IP 上设置留言板 Web 服务,以及如何使用单个主实例 (Leader) 和多个副本(关注者)运行 Redis 集群。
该示例强调了一些重要的 GKE 概念:
- 使用 YAML 清单文件的声明式配置
- Deployment,这是 Kubernetes 资源,用于确定一组副本 Pod 的配置
- Service,用于为一组 Pod 创建内部和外部负载平衡器
目标
如需在 GKE 上部署和运行留言板应用,请执行以下操作:- 设置 Redis Leader
- 设置两个 Redis 关注者
- 设置留言板 Web 前端
- 访问留言板网站
- 扩展留言板网络前端
下图展示了完成上述目标后创建的集群架构概览:
费用
在本文档中,您将使用 Google Cloud 的以下收费组件:
您可使用价格计算器根据您的预计使用情况来估算费用。
完成本文档中描述的任务后,您可以通过删除所创建的资源来避免继续计费。如需了解详情,请参阅清理。
准备工作
请按照以下步骤启用 Kubernetes Engine API:- 访问 Google Cloud 控制台中的 Kubernetes Engine 页面。
- 创建或选择项目。
- 稍作等待,让 API 和相关服务完成启用过程。 此过程可能耗时几分钟。
-
Make sure that billing is enabled for your Google Cloud project.
安装本教程中使用的以下命令行工具:
-
gcloud
用于创建和删除 Kubernetes Engine 集群。gcloud
包含在gcloud
CLI 中。 -
kubectl
用于管理 Kubernetes(即 Kubernetes Engine 使用的集群编排系统)。您可以使用gcloud
安装kubectl
:gcloud components install kubectl
设置 Google Cloud CLI 的默认值
为了节省您在 gcloud CLI 中输入项目 ID 和 Compute Engine 可用区或区域选项的时间,您可以设置默认值:gcloud config set project project-id
根据您在 GKE 中选择使用的操作模式,然后指定默认的可用区或区域。如果您使用标准模式,您的集群是可用区级(对于本教程),因此请设置您的默认计算可用区。如果您使用 Autopilot 模式,您的集群是区域级,因此请设置您的默认计算区域。
Autopilot
运行以下命令,将 compute-region
替换为您的计算区域,例如 us-west1
:
gcloud config set compute/region compute-region
标准
运行以下命令,将 compute-zone
替换为您的计算可用区,例如 us-west1-a
:
gcloud config set compute/zone compute-zone
创建 GKE 集群
第一步是创建用于运行留言板应用和 Redis 服务的 GKE 集群。
创建名为 guestbook
的 GKE 集群:
Autopilot
gcloud container clusters create-auto guestbook
标准
gcloud container clusters create guestbook --num-nodes=4
您可以使用以下命令列出项目中运行的集群:
gcloud container clusters list gcloud container clusters describe guestbook
设置 Redis Leader
留言板应用使用 Redis 来存储其数据。该应用将数据写入 Redis Leader 实例,并从多个 Redis 关注者实例中读取数据。第一步是部署 Redis Leader。
首先,克隆示例清单:
git clone https://github.com/GoogleCloudPlatform/kubernetes-engine-samples cd kubernetes-engine-samples/guestbook
使用名为 redis-leader-deployment
的清单文件部署 Redis Leader。此清单文件指定运行单个副本 Redis Leader Pod 的 Kubernetes Deployment:
运行以下命令以部署 Redis Leader:
kubectl apply -f redis-leader-deployment.yaml
验证 Redis Leader Pod 是否正在运行:
kubectl get pods输出:
NAME READY STATUS RESTARTS AGE redis-leader-343230949-qfvrq 1/1 Running 0 43s
运行以下命令以查看 Redis Leader Pod 中的日志:
kubectl logs deployment/redis-leader
输出:
1:M 24 Jun 2020 14:48:20.917 * Ready to accept connections
创建 Redis Leader 服务
留言板应用需要与 Redis Leader 通信才能写入其数据。您可以创建一个 Service 来代理传输到 Redis Leader Pod 的流量。
Service 是 Kubernetes 抽象,定义了一个逻辑 Pod 集及实现其访问权限的政策。Service 实际上是一个命名的负载平衡器,可将流量代理传输到一个或多个 Pod。 设置 Service 时,您需要根据 Pod 标签来说明要代理哪些 Pod。
查看 redis-leader-service.yaml
清单文件,该文件描述了 Redis Leader 的 Service 资源:
此清单文件创建了一项名为 redis-leader
的 Service,该 Service 带有一组标签选择器。这些标签与上一步中部署的标签集匹配。因此,该 Service 将网络流量路由到上一步中创建的 Redis Leader Pod。
清单的 ports
部分声明了单个端口映射。在本例中,此 Service 将 port: 6379
上的流量路由到匹配指定 selector
标签的容器的 targetPort:
6379
。请注意,Deployment 中使用的 containerPort
必须与 targetPort
匹配才能将流量路由到 Deployment。
通过运行以下命令来启动 Redis Leader Service:
kubectl apply -f redis-leader-service.yaml
验证 Service 已成功创建:
kubectl get service输出:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE kubernetes 10.51.240.1 <none> 443/TCP 42s redis-leader 10.51.242.233 <none> 6379/TCP 12s
设置 Redis 关注者
虽然 Redis Leader 属于单个 Pod,但您可以通过添加一些 Redis 关注者副本来为其实现高可用性,并满足流量需求。
查看 redis-follower-deployment.yaml
清单文件,该文件描述了 Redis 关注者 Pod 的 Deployment:
如需创建 Redis 关注者 Deployment,请运行以下命令:
kubectl apply -f redis-follower-deployment.yaml
通过查询 Pod 列表,验证这两个 Redis 关注者副本是否正在运行:
kubectl get pods输出:
NAME READY STATUS RESTARTS AGE redis-follower-76588f55b7-bnsq6 1/1 Running 0 27s redis-follower-76588f55b7-qvtws 1/1 Running 0 27s redis-leader-dd446dc55-kl7nl 1/1 Running 0 119s
获取其中一个 Redis 关注者的 Pod 日志。
kubectl logs deployment/redis-follower输出:
1:M 24 Jun 2020 14:50:43.617 * Background saving terminated with success 1:M 24 Jun 2020 14:50:43.617 * Synchronization with replica 10.12.3.4:6379 succeeded
创建 Redis 关注者服务
留言板应用需要与 Redis 关注者通信以读取数据。如需让 Redis 关注者更容易被发现,您必须设置其他 Service。
redis-follower-service.yaml
定义了 Redis 关注者的 Service 配置:
此文件定义一项在端口 6379 上运行的名为 redis-follower
的 Service。请注意,Service 的 selector
字段与上一步中创建的 Redis 关注者 Pod 匹配。
运行以下命令来创建 redis-follower
Service:
kubectl apply -f redis-follower-service.yaml
验证 Service 已成功创建:
kubectl get service输出:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE kubernetes 10.51.240.1 <none> 443/TCP 1m redis-leader 10.51.242.233 <none> 6379/TCP 49s redis-follower 10.51.247.238 <none> 6379/TCP 3s
设置留言板 Web 前端
在启动并运行了留言板的 Redis 存储后,可以启动留言板 Web 服务器。与 Redis 关注者一样,该前端将使用 Kubernetes Deployment 进行部署。
留言板应用使用 PHP 前端。该前端配置为根据请求属于读取请求还是写入请求,与 Redis 关注者 Service 或 Redis Leader Service 进行通信。该前端公开了一个 JSON 接口,并提供基于 jQuery-Ajax 的用户体验。
查看 frontend-deployment.yaml
清单文件,该文件描述了留言板 Web 服务器的 Deployment:
如需创建留言板 Web 前端 Deployment,请运行以下命令:
kubectl apply -f frontend-deployment.yaml
如需验证这三个副本正在运行,请查询用于标识 Web 前端的标签列表:
kubectl get pods -l app=guestbook -l tier=frontend输出:
NAME READY STATUS RESTARTS AGE frontend-7b78458576-8kp8s 1/1 Running 0 37s frontend-7b78458576-gg86q 1/1 Running 0 37s frontend-7b78458576-hz87g 1/1 Running 0 37s
清单文件指定了环境变量 GET_HOSTS_FROM=dns
。当您将配置提供给留言板 Web 前端应用时,前端应用会使用主机名 redis-follower
和 redis-leader
来执行 DNS 查找。DNS 查找将查找您在先前步骤中创建的适当 Service 的 IP 地址。此概念称为 DNS 服务发现。
在外部 IP 地址公开前端
您在先前步骤中创建的 redis-follower
和 redis-leader
Service 只能在 GKE 集群中访问,因为 Service 的默认类型是 ClusterIP
。
ClusterIP
为 Service 指向的 Pod 集提供单个 IP 地址。此 IP 地址只能在集群内访问。
但是,您需要让留言板 Web 前端 Service 可供外部用户查看。
也就是说,您希望客户端能够从 GKE 集群外部请求 Service。如需完成此请求,您可以根据需求在 Service 配置中指定 type: LoadBalancer
或 type: NodePort
。在此示例中,您将使用 type: LoadBalancer
。指定此配置的 frontend-service.yaml
清单文件如下所示:
创建 frontend
Service 时,GKE 会创建一个负载平衡器和一个外部 IP 地址。请注意,这些资源需要付费。ports
部分下方的端口声明指定了 port: 80
,未指定 targetPort
。如果忽略 targetPort
属性,则默认为 port
字段的值。在本例中,此 Service 将端口 80 上的外部流量路由到 frontend
Deployment 中容器的端口 80。
要创建 Service,请运行以下命令:
kubectl apply -f frontend-service.yaml
访问留言板网站
如需访问留言板 Service,请通过运行以下命令找到您设置的 Service 的外部 IP 地址:
kubectl get service frontend输出:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE frontend 10.51.242.136 109.197.92.229 80:32372/TCP 1m
复制 EXTERNAL-IP 列中的 IP 地址,然后在浏览器中加载页面。
如需尝试添加一些留言板条目,请尝试输入信息帖,然后点击提交。您输入的消息会显示在前端。此消息表示数据已通过您之前创建的 Service 成功添加到 Redis。
扩充 Web 前端
假设您的留言板应用已经运行了一段时间,公共宣传突然激增。您决定为前端添加更多 Web 服务器。由于您的服务器被定义为使用 Deployment 控制器的服务,因此您可以轻松进行扩展。
通过运行以下命令,将 frontend
Pod 数量扩展到 5 个:
kubectl scale deployment frontend --replicas=5
输出:
deployment.extensions/frontend scaled
系统会更新 Deployment 的配置,以指定现在应该运行 5 个副本:Deployment 会调整正在运行的 Pod 数量,以匹配配置。如需验证副本数量,请运行以下命令:
kubectl get pods输出:
NAME READY STATUS RESTARTS AGE frontend-88237173-3s3sc 1/1 Running 0 1s frontend-88237173-twgvn 1/1 Running 0 1s frontend-88237173-5p257 1/1 Running 0 23m frontend-88237173-84036 1/1 Running 0 23m frontend-88237173-j3rvr 1/1 Running 0 23m redis-leader-343230949-qfvrq 1/1 Running 0 54m redis-follower-132015689-dp23k 1/1 Running 0 37m redis-follower-132015689-xq9v0 1/1 Running 0 37m
您可以使用同一命令缩减前端 Pod 的数量。
清理
为避免因本教程中使用的资源导致您的 Google Cloud 账号产生费用,请删除包含这些资源的项目,或者保留项目但删除各个资源。
删除 Service:此步骤将取消并释放为
frontend
Service 创建的 Cloud Load Balancer:kubectl delete service frontend
等待系统完成删除为
frontend
Service 预配的负载平衡器:当您运行kubectl delete
时,系统会在后台异步删除负载平衡器。观察以下命令的输出,直到负载平衡器被删除:gcloud compute forwarding-rules list
删除 GKE 集群:此步骤将删除构成 GKE 集群的资源,如计算实例、磁盘和网络资源。
gcloud container clusters delete guestbook
后续步骤
- 了解如何使用水平 Pod 自动扩缩功能为您的 Deployment 配置自动 Pod 自动扩缩功能。
- 学习 MySQL 和 WordPress 教程,了解如何在应用中存储永久性数据。
了解如何将域名映射到 GKE Service。
浏览其他 Kubernetes Engine 教程。