使用自动修复功能构建高可用性应用


本互动教程介绍了如何使用自动修复功能在 Compute Engine 上构建高可用性应用。

高可用性应用旨在以最低的延迟和最少的停机时间向客户端提供服务。应用崩溃或冻结时,可用性会受到影响。受损应用的客户端可能会遭遇高延迟或服务中断。

借助自动修复功能,您可以自动重启受损的应用。该功能会即刻检测到故障虚拟机 (VM) 实例并自动重新创建这些实例,以便恢复正常向客户端提供服务。得益于此,您不再需要在发生故障后手动将应用恢复到正常服务状态。

目标

  • 配置健康检查和自动修复政策。
  • 在代管式实例组 (MIG) 上设置演示 Web 服务。
  • 模拟健康检查失败并见证自动修复过程。

费用

本教程使用 Google Cloud 的计费组件,包括:

  • Compute Engine

准备工作

    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.

    In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Go to project selector

    Make sure that billing is enabled for your Google Cloud project.

    Enable the Compute Engine API.

    Enable the API

    In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Go to project selector

    Make sure that billing is enabled for your Google Cloud project.

    Enable the Compute Engine API.

    Enable the API

如果您希望通过命令行进行操作,请安装 Google Cloud CLI。

  • Install the Google Cloud CLI.
  • To initialize the gcloud CLI, run the following command:

    gcloud init

应用架构

该应用包括以下 Compute Engine 组件:

  • 健康检查:自动修复程序用于检测故障虚拟机的 HTTP 健康检查政策。
  • 防火墙规则:借助 Google Cloud 防火墙规则,您可以允许或拒绝流向您的虚拟机的流量。
  • 托管实例组:运行相同的演示 Web 服务的一组虚拟机。
  • 实例模板:用于创建实例组中各个虚拟机的模板。

健康检查和实例组的系统架构。

健康检查如何探测演示 Web 服务的健康状况

健康检查使用指定的协议(如 HTTP(S)、SSL 或 TCP)向虚拟机发送探测请求。如需了解详情,请参阅健康检查原理以及健康检查类别、协议和端口

本教程中的健康检查是一个 HTTP 健康检查,它会探测端口 80 的 HTTP 路径 /health。对于 HTTP 健康检查,仅当路径返回 HTTP 200 (OK) 响应时,才算通过探测请求的检查。在本教程中,演示 Web 服务器会定义路径 /health,以便在运行状况良好时返回 HTTP 200 (OK) 响应,运行状况不佳时返回 HTTP 500 (Internal Server Error) 响应。如需了解详情,请参阅 HTTP、HTTPS、HTTP/2 成功标准

创建健康检查

要设置自动修复功能,请先创建自定义健康检查并将网络防火墙配置为允许其进行探测。

在本教程中,您将创建区域性健康检查。对于自动修复,您可以使用区域级健康检查或全球健康检查。区域级健康检查可减少跨区域依赖项并帮助实现数据驻留。如果要对多个区域中的 MIG 使用相同的健康检查,则全球健康检查会很方便。

控制台

  1. 创建健康检查。

    1. 在 Google Cloud 控制台中,前往创建健康检查页面。

      前往“创建健康检查”页面

    2. 名称字段中,输入 autohealer-check

    3. 范围设置为 Regional

    4. 区域下拉列表中,选择 europe-west1

    5. 对于协议,请选择 HTTP

    6. 请求路径设置为 /health。这表示健康检查使用的 HTTP 路径。在本教程中,演示 Web 服务器会定义路径 /health,以便在运行状况良好时返回 HTTP 200 (OK) 响应,运行状况不佳时返回 HTTP 500 (Internal Server Error) 响应。

    7. 设置运行状况判断标准

      1. 检查间隔设置为 10。这定义了从一次探测开始到下一次探测开始之间的时间量。
      2. 超时设置为 5。这定义了 Google Cloud 等待探测响应的时间量。这个值必须小于或等于检查间隔时间。
      3. 状况良好判断阈值设置为 2。这定义了要将虚拟机视为运行状况良好必须成功的连续探测次数。
      4. 状况不佳判断阈值设置为 3。这定义了要将虚拟机视为运行状况不佳所必须失败的连续探测次数。
    8. 其他选项保留默认值。

    9. 点击底部的创建

  2. 创建防火墙规则以允许健康检查发出 HTTP 探测请求。

    1. 在 Google Cloud 控制台中,转到创建防火墙规则页面。

      转到“创建防火墙规则”

    2. 对于名称,输入 default-allow-http-health-check

    3. 对于网络,请选择 default

    4. 对于目标,请选择 All instances in the network

    5. 对于来源过滤条件,请选择 IPv4 ranges

    6. 对于来源 IPv4 范围,输入 130.211.0.0/22, 35.191.0.0/16

    7. 协议和端口中,选择 TCP 并输入 80

    8. 其他选项保留默认值。

    9. 点击创建

gcloud

  1. 使用 health-checks create http 命令创建健康检查。

    gcloud compute health-checks create http autohealer-check \
        --region europe-west1 \
        --check-interval 10 \
        --timeout 5 \
        --healthy-threshold 2 \
        --unhealthy-threshold 3 \
        --request-path "/health"
    
    • check-interval 定义了从一次探测开始到下一次探测开始之间的时间量。
    • timeout 定义了 Google Cloud 等待探测响应的时间量。这个值必须小于或等于检查间隔时间。
    • healthy-threshold 定义了要将虚拟机视为运行状况良好必须成功的连续探测次数。
    • unhealthy-threshold 定义了要将虚拟机视为运行状况不佳所必须失败的连续探测次数。
    • request-path 表示健康检查使用的 HTTP 路径。在本教程中,演示 Web 服务器会定义路径 /health,以便在运行状况良好时返回 HTTP 200 (OK) 响应,运行状况不佳时返回 HTTP 500 (Internal Server Error) 响应。
  2. 创建防火墙规则以允许健康检查发出 HTTP 探测请求。

    gcloud compute firewall-rules create default-allow-http-health-check \
        --network default \
        --allow tcp:80 \
        --source-ranges 130.211.0.0/22,35.191.0.0/16
    

良好的自动修复健康检查需要具备哪些特点

自动修复健康检查应该比较保守,以免在不必要时删除并重新创建实例。如果为自动修复功能设置的健康检查过于严格,则自动修复程序可能会将繁忙的实例误认为故障实例,并且不必要地重启它们,从而降低可用性。

  • unhealthy-threshold。此值应大于 1。最好将此值设置为 3 或更大。这样可以防止在发生网络数据包丢失等罕见故障时误判。
  • healthy-threshold。对于大多数应用来说,将此值设置为 2 就足够了。
  • timeout。请将此时间值设置为一个较大的值(预期响应时间的五倍或更长时间)。这样可以防止在出现意外延迟(例如实例繁忙或网络拥堵造成的延迟)时误判。
  • check-interval。此值应介于 1 秒到超时的两倍之间(不要太长,也不要太短)。如果设置的时间太长,就不能及时发现故障实例。如果设置的时间太短,实例和网络可能会因健康检查每秒发送大量探测而变得非常繁忙。

设置 Web 服务

本教程使用一个存储在 GitHub 上的 Web 应用。如果您想详细了解该应用的实现方式,请参阅 GoogleCloudPlatform/python-docs-samples GitHub 代码库。

要设置演示 Web 服务,请先创建一个在启动时会自动启动演示 Web 服务器的实例模板。然后,使用此实例模板部署托管实例组并启用自动修复功能。

控制台

  1. 创建实例模板。其中包含用于启动演示 Web 服务器的启动脚本。

    1. 在 Google Cloud 控制台中,前往创建实例模板页面。

      前往“创建实例模板”页面

    2. 名称设置为 webserver-template

    3. 位置部分,从区域下拉菜单中选择 europe-west1

    4. 机器配置部分中,选择 e2-medium 作为机器类型下拉菜单中的选项。

    5. 防火墙部分,选中允许 HTTP 流量复选框。

    6. 展开高级选项部分以显示高级设置。系统会显示多个子部分。

    7. 管理部分,找到自动化并输入以下启动脚本

      apt update && apt -y install git python3-pip python3-venv
      git clone https://github.com/GoogleCloudPlatform/python-docs-samples.git
      python3 -m venv venv
      ./venv/bin/pip3 install -Ur ./python-docs-samples/compute/managed-instances/demo/requirements.txt
      ./venv/bin/pip3 install gunicorn
      ./venv/bin/gunicorn --bind 0.0.0.0:80 app:app --daemon --chdir ./python-docs-samples/compute/managed-instances/demo
      

    8. 其他选项保留默认值。

    9. 点击创建

  2. 将 Web 服务器部署为托管式实例组。

    1. 在 Google Cloud 控制台中,前往创建实例组页面。

      前往“创建实例组”页面

    2. 名称设置为 webserver-group

    3. 对于实例模板,请选择 webserver-template

    4. 对于区域,请选择 europe-west1

    5. 对于可用区,请选择 europe-west1-b

    6. 自动扩缩部分中,对于自动扩缩模式,选择关闭:不自动扩缩

    7. 滚动回实例数字段,将其设置为 3

    8. 自动修复部分,执行以下操作:

      1. 健康检查下拉列表中,选择 autohealer-check
      2. 初始延迟时间设置为 180

    9. 其他选项保留默认值。

    10. 点击创建

  3. 创建一条允许向 Web 服务器发出 HTTP 请求的防火墙规则。

    1. 在 Google Cloud 控制台中,转到创建防火墙规则页面。

      转到“创建防火墙规则”

    2. 对于名称,输入 default-allow-http

    3. 对于网络,请选择 default

    4. 对于目标,请选择 Specified target tags

    5. 对于目标标记,请输入 http-server

    6. 对于来源过滤条件,请选择 IPv4 ranges

    7. 对于来源 IPv4 范围,输入 0.0.0.0/0

    8. 协议和端口中,选择 TCP 并输入 80

    9. 其他选项保留默认值。

    10. 点击创建

gcloud

  1. 创建实例模板。在其中添加用于启动演示 Web 服务器的启动脚本。

    gcloud compute instance-templates create webserver-template \
        --instance-template-region europe-west1 \
        --machine-type e2-medium \
        --tags http-server \
        --metadata startup-script='
      apt update && apt -y install git python3-pip python3-venv
      git clone https://github.com/GoogleCloudPlatform/python-docs-samples.git
      python3 -m venv venv
      ./venv/bin/pip3 install -Ur ./python-docs-samples/compute/managed-instances/demo/requirements.txt
      ./venv/bin/pip3 install gunicorn
      ./venv/bin/gunicorn --bind 0.0.0.0:80 app:app --daemon --chdir ./python-docs-samples/compute/managed-instances/demo'
    
  2. 创建托管式实例组。

    gcloud compute instance-groups managed create webserver-group \
        --zone europe-west1-b \
        --template projects/PROJECT_ID/regions/europe-west1/instanceTemplates/webserver-template \
        --size 3 \
        --health-check projects/PROJECT_ID/regions/europe-west1/healthChecks/autohealer-check \
        --initial-delay 180
    
  3. 创建一条允许向 Web 服务器发出 HTTP 请求的防火墙规则。

    gcloud compute firewall-rules create default-allow-http \
        --network default \
        --allow tcp:80 \
        --target-tags http-server
    

等待几分钟,让代管式实例组创建并验证其虚拟机。

模拟健康检查失败

为了模拟健康检查失败的情况,演示 Web 服务器提供了几种强制使健康检查失败的方法。

控制台

  1. 前往 Web 服务器虚拟机。

    1. 在 Google Cloud 控制台中,前往虚拟机实例页面。

      转到虚拟机实例

    2. 对于任何 webserver-group 虚拟机,请在外部 IP 列下,点击相应 IP 地址。网络浏览器中会打开一个新的标签页。如果请求超时或网页不可用,请等待服务器完成设置,然后重试。

    演示 Web 服务器会显示一个内容大致如下的网页:

    显示绿色状态按钮和蓝色操作按钮的简单演示网页

  2. 在演示网页上,点击模拟运行状况不佳 (Make unhealthy)。

    这会导致 Web 服务器使健康检查失败。具体而言,Web 服务器会使 /health 路径返回 HTTP 500 (Internal Server Error)。只需紧接着点击检查运行状况 (Check health) 按钮,您即可自行验证这一点(自动修复程序开始重新启动虚拟机后,该方法即告失效)。

  3. 等待自动修复程序采取行动。

    1. 在 Google Cloud 控制台中,前往虚拟机实例页面。

      转到虚拟机实例

    2. 等待 Web 服务器虚拟机的状态发生变化。虚拟机名称旁边的绿色对勾标记应变为灰色方块,这表示自动修复程序已开始重新启动运行状况不佳的虚拟机。

    3. 定期点击页面顶部的刷新以获取最新状态。

    4. 当灰色方块变回绿色对勾标记时,表示虚拟机已恢复至正常运行状态,此时自动修复过程就完成了。

gcloud

  1. 监控代管式实例组的状态。(完成后,请按 Ctrl+C 键停止。)

    while : ; do \
        gcloud compute instance-groups managed list-instances webserver-group \
        --zone europe-west1-b \
        ; done
    
      NAME: webserver-group-0zx6
      ZONE: europe-west1-b
      STATUS: RUNNING
      HEALTH_STATE: HEALTHY
      ACTION: NONE
      INSTANCE_TEMPLATE: webserver-template
      VERSION_NAME:
      LAST_ERROR:
    
      NAME: webserver-group-4qbx
      ZONE: europe-west1-b
      STATUS: RUNNING
      HEALTH_STATE: HEALTHY
      ACTION: NONE
      INSTANCE_TEMPLATE: webserver-template
      VERSION_NAME:
      LAST_ERROR:
    
      NAME: webserver-group-m5v5
      ZONE: europe-west1-b
      STATUS: RUNNING
      HEALTH_STATE: HEALTHY
      ACTION: NONE
      INSTANCE_TEMPLATE: webserver-template
      VERSION_NAME:
      LAST_ERROR:
    

    群组中的所有虚拟机都必须显示 STATUS: RUNNINGACTION: NONE。如果没有,请等待几分钟,让虚拟机完成设置,然后重试。

  2. 使用安装的 Google Cloud CLI 打开新的 Cloud Shell 会话。

  3. 获取 Web 服务器虚拟机的地址。

    gcloud compute instances list --filter webserver-group
    

    EXTERNAL_IP 列下,复制任意 Web 服务器虚拟机的 IP 地址并将其另存为本地 bash 变量。

    export IP_ADDRESS=EXTERNAL_IP_ADDRESS
    
  4. 验证 Web 服务器是否已完成设置。服务器返回 HTTP 200 OK 响应。

    curl --head $IP_ADDRESS/health
    
    HTTP/1.1 200 OK
    Server: gunicorn
    ...
    

    如果您收到 Connection refused 错误,请等待服务器完成设置,然后重试。

  5. 让 Web 服务器模拟运行状况不佳时的状况。

    curl $IP_ADDRESS/makeUnhealthy > /dev/null
    

    这会导致 Web 服务器使健康检查失败。具体而言,Web 服务器会使 /health 路径返回 HTTP 500 INTERNAL SERVER ERROR。只需紧接着向 /health 发出一个请求,您即可自行验证这一点(自动修复程序开始重新启动虚拟机后,该方法即告失效)。

    curl --head $IP_ADDRESS/health
    
    HTTP/1.1 500 INTERNAL SERVER ERROR
    Server: gunicorn
    ...
    
  6. 返回到第一个 Shell 会话以监控代管式实例组并等待自动修复程序执行操作。

    1. 自动修复过程开始后,STATUSACTION 列将会更新,这表示自动修复程序已开始重新启动运行状况不佳的虚拟机。

        NAME: webserver-group-0zx6
        ZONE: europe-west1-b
        STATUS: STOPPING
        HEALTH_STATE: UNHEALTHY
        ACTION: RECREATING
        INSTANCE_TEMPLATE: webserver-template
        VERSION_NAME:
        LAST_ERROR:
      
        ...
      
    2. 当虚拟机再次报告 STATUSRUNNINGACTIONNONE 时,表示虚拟机已经成功重启,此时自动修复过程已完成。

        NAME: webserver-group-0zx6
        ZONE: europe-west1-b
        STATUS: RUNNING
        HEALTH_STATE: HEALTHY
        ACTION: NONE
        INSTANCE_TEMPLATE: webserver-template
        VERSION_NAME:
        LAST_ERROR:
      
        ...
      
    3. 完成对代管式实例组的监控后,请按 Ctrl+C 键停止。

请随意重复这一练习。以下是一些建议:

  • 如果您一次使所有虚拟机都进入运行状况不佳的状态,将会怎样?如需详细了解发生并发故障时的自动修复行为,请参阅自动修复行为

  • 能否更新健康检查配置,以尽快修复虚拟机?(在实际使用中,您应该按照本教程中所述,将健康检查参数设置为保守值。否则,虚拟机可能会在其实未发生问题的情况下被误删并重启。)

  • 代管式实例组具有 initial delay 配置设置。您能确定此演示 Web 服务器所需的最小延迟吗?(在实际使用中,您应该将延迟设为稍微(10-20%)长于虚拟机完成启动并可开始处理应用请求所需的时间。否则,虚拟机可能会陷入自动修复启动循环中。)

查看自动修复程序的历史记录(可选)

如需查看自动修复程序的操作历史记录,请使用以下 gcloud 命令:

gcloud compute operations list --filter='operationType~compute.instances.repair.*'

如需了解详情,请参阅查看历史自动修复操作

清理

完成本教程后,您可以清理您创建的资源,让它们停止使用配额,以免产生费用。以下部分介绍如何删除或关闭这些资源。

如果您为本教程创建了单独的项目,请删除整个项目。 否则,如果项目中包含您要保留的资源,则只删除在本教程中创建的特定资源。

删除项目

  1. In the Google Cloud console, go to the Manage resources page.

    Go to Manage resources

  2. In the project list, select the project that you want to delete, and then click Delete.
  3. In the dialog, type the project ID, and then click Shut down to delete the project.

删除特定资源

如果您无法删除本教程中使用的项目,请单独删除教程资源。

删除实例组

控制台

  1. In the Google Cloud console, go to the Instance groups page.

    Go to Instance groups

  2. Select the checkbox for your webserver-group instance group.
  3. To delete the instance group, click Delete.

gcloud

gcloud compute instance-groups managed delete webserver-group --zone europe-west1-b -q

删除实例模板

控制台

  1. 在 Google Cloud 控制台中,转到实例模板页面。

    转到“实例模板”

  2. 点击实例模板旁边的复选框。

  3. 点击页面顶部的 删除。在新窗口中,点击删除以确认删除。

gcloud

gcloud compute instance-templates delete webserver-template -q

删除健康检查

控制台

  1. 在 Google Cloud 控制台中,转到健康检查页面。

    转到“健康检查”

  2. 点击健康检查旁边的复选框。

  3. 点击页面顶部的 删除。在新窗口中,点击删除以确认删除。

gcloud

gcloud compute health-checks delete autohealer-check -q

删除防火墙规则

控制台

  1. 在 Google Cloud 控制台中,转到防火墙规则页面。

    转到“防火墙规则”

  2. 点击名为 default-allow-httpdefault-allow-http-health-check 的防火墙规则旁边的复选框。

  3. 点击页面顶部的 删除。在新窗口中,点击删除以确认删除。

gcloud

gcloud compute firewall-rules delete default-allow-http default-allow-http-health-check -q

后续步骤