本教程演示了如何使用 Google Kubernetes Engine (GKE) 构建多层 Web 应用。
在本教程中,您将执行以下操作:
- 使用外部 IP 地址和负载均衡器设置 Web 应用。
- 创建一个包含单个主实例 (Leader) 和多个副本(Follower)的 Redis 集群。
该示例介绍了以下 Kubernetes 概念:
- 使用 YAML 清单文件的声明式配置
- Deployment,这是 Kubernetes 资源,用于确定一组副本 Pod 的配置
- Service,用于为一组 Pod 创建内部和外部负载平衡器
目标
如需在 GKE 上部署和运行应用,请执行以下操作:- 设置 Redis Leader
- 设置两个 Redis 关注者
- 设置 Web 前端
- 访问网站
- 扩展 Web 前端
下图展示了完成上述目标后创建的集群架构概览:
费用
在本文档中,您将使用 Google Cloud 的以下收费组件:
您可使用价格计算器根据您的预计使用情况来估算费用。
完成本文档中描述的任务后,您可以通过删除所创建的资源来避免继续计费。如需了解详情,请参阅清理。
准备工作
Cloud Shell 中预安装了本教程所需的软件,包括 kubectl
和 gcloud CLI。如果您不使用 Cloud Shell,则必须安装 gcloud CLI。
- Sign in to your Google Cloud account. If you're new to Google Cloud, create an account to evaluate how our products perform in real-world scenarios. New customers also get $300 in free credits to run, test, and deploy workloads.
- Install the Google Cloud CLI.
-
To initialize the gcloud CLI, run the following command:
gcloud init
-
Create or select a Google Cloud project.
-
Create a Google Cloud project:
gcloud projects create PROJECT_ID
Replace
PROJECT_ID
with a name for the Google Cloud project you are creating. -
Select the Google Cloud project that you created:
gcloud config set project PROJECT_ID
Replace
PROJECT_ID
with your Google Cloud project name.
-
-
Make sure that billing is enabled for your Google Cloud project.
-
Enable the GKE API:
gcloud services enable container.googleapis.com
- Install the Google Cloud CLI.
-
To initialize the gcloud CLI, run the following command:
gcloud init
-
Create or select a Google Cloud project.
-
Create a Google Cloud project:
gcloud projects create PROJECT_ID
Replace
PROJECT_ID
with a name for the Google Cloud project you are creating. -
Select the Google Cloud project that you created:
gcloud config set project PROJECT_ID
Replace
PROJECT_ID
with your Google Cloud project name.
-
-
Make sure that billing is enabled for your Google Cloud project.
-
Enable the GKE API:
gcloud services enable container.googleapis.com
准备环境
如需设置您的环境,请按以下步骤操作:
设置环境变量:
export PROJECT_ID=PROJECT_ID export COMPUTE_LOCATION=COMPUTE_LOCATION
替换以下内容:
PROJECT_ID
:您的 Google Cloud 项目 IDCOMPUTE_LOCATION
:Compute Engine 位置,例如us-central1
。
克隆 GitHub 代码库:
git clone https://github.com/GoogleCloudPlatform/kubernetes-engine-samples
切换到工作目录:
cd kubernetes-engine-samples/quickstarts/guestbook/
创建 GKE 集群
创建 Autopilot 或 Standard GKE 集群:
Autopilot
gcloud container clusters create-auto guestbook \
--location=${COMPUTE_LOCATION} \
Standard
gcloud container clusters create guestbook \
--location=${COMPUTE_LOCATION} \
--num-nodes=4
连接到集群
配置 kubectl
以与集群通信:
gcloud container clusters get-credentials guestbook \
--location=${COMPUTE_LOCATION}
设置 Redis Leader
该应用使用 Redis 来存储其数据。该应用将数据写入 Redis Leader 实例,并从多个 Redis 关注者实例中读取数据。
以下清单描述了一个运行单个副本 Redis 主实例 Pod 的 Kubernetes Deployment:
将清单应用到您的集群:
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
STATUS
可能需要几分钟才能从Pending
变为Running
。
创建 Redis Leader 服务
该 Web 应用需要与 Redis Leader 通信才能写入其数据。您可以创建一个 Service 来代理传输到 Redis Leader Pod 的流量。
Service 是 Kubernetes 抽象,定义了一个逻辑 Pod 集及实现其访问权限的政策。创建 Service 时,您需要根据 Pod 标签来说明要代理哪些 Pod。
以下清单描述了 Redis Leader 的 Service:
此清单包含一组标签选择器。这些标签与上一步中部署的标签集匹配。因此,该 Service 将网络流量路由到上一步中创建的 Redis Leader Pod。
清单的
ports
部分声明了单个端口映射。此 Service 将port: 6379
上的流量路由到匹配指定selector
标签的容器的targetPort: 6379
。Deployment 中使用的containerPort
必须与targetPort
匹配才能将流量路由到 Deployment。将清单应用到您的集群:
kubectl apply -f redis-leader-service.yaml
验证 GKE 是否已创建该 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 关注者 Pod 的 Deployment:
将清单应用到您的集群:
kubectl apply -f redis-follower-deployment.yaml
验证这两个 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
STATUS
可能需要几分钟才能从Pending
变为Running
。
创建 Redis 关注者服务
Web 应用必须与 Redis 关注者通信才能读取数据。如需让 Redis 关注者更容易被发现,您必须设置一项 Service。
以下清单描述了 Redis 从属服务:
此清单指定该 Service 在端口 6379 上运行。Service 的
selector
字段与上一步中创建的 Redis 关注者 Pod 匹配。将清单应用到您的集群:
kubectl apply -f redis-follower-service.yaml
验证 GKE 是否已创建该 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 进行部署。
Web 应用使用 PHP 前端,该前端配置为根据请求属于读取请求还是写入请求,与 Redis 关注者 Service 或 Redis Leader Service 进行通信。该前端公开了一个 JSON 接口,并提供基于 jQuery Ajax 的界面。
以下清单描述了 Web 服务器的部署:
清单文件指定了环境变量
GET_HOSTS_FROM=dns
。当您将配置提供给 Web 前端应用时,前端应用会使用主机名redis-follower
和redis-leader
来执行 DNS 查找。DNS 查找将查找您在上一步中创建的 Service 的 IP 地址。此概念称为 DNS 服务发现。将清单应用到您的集群:
kubectl apply -f frontend-deployment.yaml
验证副本是否正在运行:
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
在外部 IP 地址公开前端
在当前配置下,您在前面步骤中创建的 redis-follower
和 redis-leader
服务只能在 GKE 集群中访问,因为 Service 的默认类型是 ClusterIP
。
ClusterIP
Service 为 Service 指向的 Pod 集提供单个 IP 地址。此 IP 地址只能在集群内访问。
如需使 Web 前端服务可供外部访问,您可以根据需求在 Service 配置中指定 type: LoadBalancer
或 type: NodePort
。
以下清单描述了 LoadBalancer 类型的 Service:
ports
部分下方的端口声明指定了 port: 80
,未指定 targetPort
。如果您省略 targetPort
属性,则其将默认为 port
字段的值。在本例中,此 Service 将端口 80 上的外部流量路由到 frontend
Deployment 中容器的端口 80。
将清单应用到您的集群:
kubectl apply -f frontend-service.yaml
创建 frontend
Service 时,GKE 会创建一个负载均衡器和一个外部 IP 地址。这些资源需要付费。
访问应用网站
如需访问应用网站,请获取 frontend
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
列可能会显示 <pending>
。这可能需要几分钟的时间。如果您看到 Does not have minimum availability
等错误,请等待几分钟。出现此暂时性错误是因为 GKE 会重新创建节点以进行更改。
复制 IP 地址,然后在浏览器中打开该页面:
如需尝试添加一些留言板条目,请尝试输入信息帖,然后点击提交。您输入的消息会显示在前端。此消息表示数据已通过您创建的 Service 成功添加到 Redis。
扩展 Web 前端
假设您的应用已经运行了一段时间,公共宣传突然激增。您决定为前端添加更多 Web 服务器。为此,您可以增加 Pod 的数量。
扩缩
frontend
Pod 的数量:kubectl scale deployment frontend --replicas=5
输出类似于以下内容:
deployment.extensions/frontend scaled
验证正在运行的副本数:
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
您可以使用相同的命令缩减
frontend
Pod 的数量,只需将5
替换为1
即可。
清理
为避免因本教程中使用的资源导致您的 Google Cloud 账号产生费用,请删除包含这些资源的项目,或者保留项目但删除各个资源。
删除项目
Delete a Google Cloud project:
gcloud projects delete PROJECT_ID
逐个删除资源
如果您使用的是现有项目,并且不想将其删除,请逐个删除资源。
删除
frontend
服务:kubectl delete service frontend
删除 GKE 集群:
gcloud container clusters delete guestbook