跨多个后端服务器进行负载均衡

您正在查看 Apigee Edge 文档。
转到 Apigee X 文档
信息

Apigee Edge 通过为多个后端服务器实例之间的负载均衡和故障切换提供内置支持,提高了 API 的可用性。

TargetServer 配置将具体端点网址与 TargetEndpoint 配置分离开来。每个 TargetServer 都在 TargetEndpoint HTTPConnection 中按名称引用。您可以按照 TargetEndpoint 部分的说明配置一个或多个已命名的 TargetServer,而不是在配置中定义具体的网址。

TargetServer 定义由名称、主机和端口组成,还有一个额外的元素用于指示 TargetServer 是启用还是停用。

视频

观看以下视频,详细了解如何使用目标服务器进行 API 路由和负载均衡

视频 说明
使用目标服务器实现负载均衡 跨目标服务器的负载均衡 API。
根据环境使用目标服务器路由 API 根据环境将 API 路由到其他目标服务器。
使用目标服务器进行 API 路由和负载均衡(传统边缘) 根据环境将 API 路由到其他目标服务器,并在传统版 Edge 界面中对目标服务器之间的 API 进行负载均衡。

TargetServer 配置示例

以下代码定义目标服务器:

<TargetServer  name="target1">
  <Host>1.mybackendservice.com</Host>
  <Port>80</Port>
  <IsEnabled>true</IsEnabled>
</TargetServer >

TargetServer 配置元素

下表介绍了用于创建和配置 TargetServer 的元素:

名称 说明 默认 是否必需?
name TargetServer 配置的名称,在环境中必须是唯一的。TargetServer 名称只能包含字母数字字符。 不适用
Host

后端服务的主机网址(不带协议)。

不适用
Port 后端服务监听的端口 不适用
IsEnabled 指示启用还是停用 TargetServer 配置的布尔值。 这样,您就可以在不修改 API 代理配置的情况下停用 TargetServer。一种常见用法是编写一个应用或脚本,以根据预期的容量要求、维护时间表等自动启用或停用 TargetServer。 true

使用界面管理目标服务器

管理目标服务器,具体如下所述。

Edge

如需使用 Edge 界面管理目标服务器,请执行以下操作:

  1. 登录 apigee.com/edge
  2. 在左侧导航栏中依次选择管理 > 环境 > 目标服务器
  3. 选择所需的环境,例如 testprod
  4. 如需创建目标服务器,请执行以下操作:
    1. 点击 + 目标服务器
    2. 输入目标服务器的名称、主机和端口。

      例如:

      • 名称:target1
      • 主机:1.mybackendservice.com
      • 端口:80
    3. 根据需要选择 SSL
    4. 选择已启用以启用目标服务器。
    5. 点击添加
  5. 如需修改目标服务器,请执行以下操作:
    1. 将光标置于要修改的目标服务器上方,以显示操作菜单。
    2. 点击
    3. 修改 targer 服务器值。
    4. 点击更新
  6. 如需删除目标服务器,请执行以下操作:
    1. 将光标放在要删除的目标服务器上,以显示操作菜单。
    2. 点击
    3. 点击删除以确认操作。

传统 Edge (Private Cloud)

如需使用传统版 Edge 界面访问“创建代理”向导,请执行以下操作:

  1. 登录 http://ms-ip:9000,其中 ms-ip 是管理服务器节点的 IP 地址或 DNS 名称。
  2. 在左侧导航栏中依次选择 API > 环境配置 > 目标服务器
  3. 选择所需的环境,例如 testprod
  4. 如需创建目标服务器,请执行以下操作:
    1. 点击修改
    2. 点击 + 目标服务器
    3. 输入目标服务器的名称、主机和端口。

      例如:

      • 名称:target1
      • 主机:1.mybackendservice.com
      • 端口:80
    4. 选择已启用以启用目标服务器。
    5. 点击保存
  5. 如需修改目标服务器,请执行以下操作:
    1. 点击修改
    2. 修改 targer 服务器值。
    3. 点击保存
  6. 如需删除目标服务器,请执行以下操作:
    1. 点击修改
    2. 点击删除

使用 API 管理目标服务器

您可以使用 Edge API 创建、删除、更新、获取和列出目标服务器。如需了解详情,请参阅 TargetServers

使用以下 API 调用创建目标服务器:

$ curl -H "Content-Type:text/xml" -X POST -d \
'<TargetServer name="target1">
   <Host>1.mybackendservice.com</Host>
   <Port>80</Port>
   <IsEnabled>true</IsEnabled>
 </TargetServer>' \
-u email:password https://api.enterprise.apigee.com/v1/o/{org_name}/environments/test/targetservers

示例响应:

{
  "host" : "1.mybackendservice.com",
  "isEnabled" : true,
  "name" : "target1",
  "port" : 80
}

创建第一个 TargetServer 后,使用以下 API 调用创建第二个 TargetServer。通过定义两个 TargetServer,您提供了两个可供 TargetEndpoint 用于负载均衡的网址:

$ curl -H "Content-type:text/xml" -X POST -d \
'<TargetServer  name="target2">
  <Host>2.mybackendservice.com</Host>
  <Port>80</Port>
  <IsEnabled>true</IsEnabled>
</TargetServer >' \
-u email:password https://api.enterprise.apigee.com/v1/o/{org_name}/environments/test/targetservers

示例响应:

{
  "host" : "2.mybackendservice.com",
  "isEnabled" : true,
  "name" : "target2",
  "port" : 80
}

使用以下 API 调用来检索环境中的 TargetServer 列表:

$ curl -u email:password https://api.enterprise.apigee.com/v1/o/{org_name}/environments/test/targetservers

示例响应:

[ "target2", "target1" ]

现在有两个 TargetServer 可供测试环境中部署的 API 代理使用。为了在这些 TargetServer 之间实现流量负载均衡,您需要将 API 代理的目标端点中的 HTTP 连接配置为使用 TargetServer。

每个环境最多只能有 500 个 TargetServer,详情请参阅限制主题。

配置 TargetEndpoint 以便对已命名的 TargetServer 进行负载均衡

现在有两个 TargetServer 可用,您可以修改 TargetEndpoint HTTP 连接设置,以按名称引用这两个 TargetServer:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
    <LoadBalancer>
      <Server name="target1" />
      <Server name="target2" />
    </LoadBalancer>
    <Path>/test</Path>
  </HTTPTargetConnection>
</TargetEndpoint>

上述配置是最基本的负载均衡配置。负载均衡器支持三种负载均衡算法:轮询、加权和最少连接。轮询是默认算法。由于上述配置中未指定算法,因此从 API 代理到后端服务器的出站请求将在 target1 和目标 2 之间交替进行。

<Path> 元素构成了所有目标服务器的 TargetEndpoint URI 的基本路径。只有在使用 <LoadBalancer> 时才能使用该元素。否则会忽略该元素。在上面的示例中,发送到“target1”的请求将为 http://target1/test,对于其他目标服务器,也是如此。

设置负载平衡器选项

您可以使用负载平衡器和 TargetServer 层级的负载均衡和故障切换选项调整可用性。本部分介绍了这些选项。

算法

设置 <LoadBalancer> 使用的算法。可用的算法包括 RoundRobinWeightedLeastConnections,每个算法详见下文。

轮循

默认算法(即轮询)按照服务器在目标端点 HTTP 连接中的列出顺序将请求转发给每个 TargetServer。例如:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
      <LoadBalancer>
        <Algorithm>RoundRobin</Algorithm>
        <Server name="target1" />
        <Server name="target2" />
      </LoadBalancer>
      <Path>/test</Path>
  </HTTPTargetConnection>
</TargetEndpoint>

加权

通过加权负载均衡算法,您可以为 TargetServer 配置成比例的流量负载。加权 LoadBalancer 根据每个 TargetServer 的权重成正比将请求分配到 TargetServer。因此,加权算法要求您为每个 TargetServer 设置 weight 属性。例如:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
    <LoadBalancer>
      <Algorithm>Weighted</Algorithm>
      <Server name="target1">
        <Weight>1</Weight>
      </Server>
      <Server name="target2">
        <Weight>2</Weight>
      </Server>
    </LoadBalancer>
    <Path>/test</Path>
  </HTTPTargetConnection>
</TargetEndpoint>

在此示例中,每次向 target1 路由一个请求时,都将向 target2 路由两个请求。

最少连接

配置成使用最少连接算法的 LoadBalancer 可将出站请求路由到打开的 HTTP 连接数量最少的 TargetServer。例如:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
      <LoadBalancer>
        <Algorithm>LeastConnections</Algorithm>
        <Server name="target1" />
        <Server name="target2" />
      </LoadBalancer>
  </HTTPTargetConnection>
  <Path>/test</Path>
</TargetEndpoint>

失败次数上限

从 API 代理发送到 TargetServer(它将请求重定向至另一个 TargetServer)的失败请求数量上限。

响应失败意味着 Apigee 未收到目标服务器的任何响应。当出现这种情况时,失败计数器会加 1。

但是,当 Apigee 确实收到来自目标的响应时,即使响应为 HTTP 错误(如 500),也会计为来自目标服务器的响应,并且失败计数器会被重置。为了确保不良 HTTP 响应(例如 500)也会递增失败计数器,使运行状况不佳的服务器尽快退出负载均衡轮替,您可以将包含 <ResponseCode> 子元素的 <ServerUnhealthyResponse> 元素添加到负载平衡器配置中。Edge 还会将这些代码的响应计为失败。

在以下示例中,target1 将在 5 次失败的请求(包括来自目标服务器的一些 5XX 响应)后从轮替中移除。

<TargetEndpoint name="default">
  <HTTPTargetConnection>
      <LoadBalancer>
        <Algorithm>RoundRobin</Algorithm>
        <Server name="target1" />
        <Server name="target2" />
        <MaxFailures>5</MaxFailures>
        <ServerUnhealthyResponse>
            <ResponseCode>500</ResponseCode>
            <ResponseCode>502</ResponseCode>
            <ResponseCode>503</ResponseCode>
        </ServerUnhealthyResponse>
      </LoadBalancer>
      <Path>/test</Path>
  </HTTPTargetConnection>
</TargetEndpoint>

MaxFailures 默认值为 0。 这意味着 Edge 始终会尝试连接到每个请求的目标,并且永远不会从轮替中移除目标服务器。

最好将 MaxFailures > 0 与 HealthMonitor 搭配使用。 如果配置的 MaxFailures 大于 0,则当目标失败的次数达到您指定的次数时,TargetServer 会从轮替中移除。如果 HealthMonitor 落实到位,则 Apigee 会根据 HealthMonitor 的配置,在目标重新启动并再次运行后,自动使 TargetServer 正常运行。如需了解详情,请参阅运行状况监控

或者,如果您配置 MaxFailures > 0,并且未配置 HealthMonitor,则在检测到失败后,Apigee 将不会自动将 TargetServer 重新纳入轮替。在这种情况下,您必须重新部署 API 代理,然后 Apigee 才会将 TargetServer 重新纳入轮替。请参阅部署 API 代理

重试

如果启用了重试功能,则每当响应失败(发生 I/O 错误或 HTTP 超时)或收到的响应与 <ServerUnhealthyResponse> 设置的值匹配时,系统就会重试请求。如需详细了解如何设置 <ServerUnhealthyResponse>,请参阅上面的失败次数上限

默认情况下,<RetryEnabled> 设置为 true。设置为 false 可停用重试功能。例如:

<RetryEnabled>false</RetryEnabled>

IsFallback

只能将一个 TargetServer 设置为后备服务器。在负载平衡器将所有其他 TargetServer 标识为不可用之前,后备 TargetServer 不会纳入负载平衡例程。当负载均衡器确定所有 TargetServer 均不可用时,所有流量都会路由到后备服务器。例如:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
      <LoadBalancer>
        <Algorithm>RoundRobin</Algorithm>
        <Server name="target1" />
        <Server name="target2" />
        <Server name="target3">
          <IsFallback>true</IsFallback>
        </Server>
      </LoadBalancer>
      <Path>/test</Path>
  </HTTPTargetConnection>
</TargetEndpoint>

以上配置会导致目标 1 和 2 之间进行轮询负载平衡,直到目标 1 和 2 都不可用。当目标 1 和 2 均不可用时,所有流量都会路由到目标 3。

路径

路径定义一个 URI 片段,该片段将会附加到 TargetServer 向后端服务器发出的所有请求。

此元素接受字面量字符串路径或消息模板。借助消息模板,您可以在运行时执行变量字符串替换操作。例如,在以下目标端点定义中,{mypath} 的值用于路径:

<HTTPTargetConnection>
    <SSLInfo>
      <Enabled>true</Enabled>
    </SSLInfo>
    <LoadBalancer>
      <Server name="testserver"/>
    </LoadBalancer>
    <Path>{mypath}</Path>
</HTTPTargetConnection>

为 TLS/SSL 配置目标服务器

如果您使用 TargetServer 定义后端服务,且后端服务要求连接使用 HTTPS 协议,则您必须在 TargetServer 定义中启用 TLS/SSL。您必须这样做,因为 <Host> 标记不支持指定连接协议。下面显示了单向 TLS/SSL 的 TargetServer 定义,其中 Edge 向后端服务发出 HTTPS 请求:

<TargetServer name="target1">
  <Host>mocktarget.apigee.net</Host>
  <Port>443</Port>
  <IsEnabled>true</IsEnabled>
  <SSLInfo>
      <Enabled>true</Enabled>
  </SSLInfo> 
</TargetServer>

如果后端服务需要双向 TLS/SSL,您可以使用与 TargetEndpoints 相同的 TLS/SSL 设置来配置 TargetServer:

<TargetServer  name="TargetServer 1">
    <IsEnabled>true</IsEnabled>
    <Host>www.example.com</Host>
    <Port>443</Port>
    <SSLInfo>
        <Ciphers/>
        <ClientAuthEnabled>true</ClientAuthEnabled>
        <Enabled>true</Enabled>
        <IgnoreValidationErrors>false</IgnoreValidationErrors>
        <KeyAlias>keystore-alias</KeyAlias>
        <KeyStore>keystore-name</KeyStore>
        <Protocols/>
        <TrustStore>truststore-name</TrustStore>
    </SSLInfo>
</TargetServer >

如需了解 <SSLInfo> 属性(例如 <Ciphers><ClientAuthEnabled>),请参阅为私有云配置对 API 的 TLS 访问权限,了解如何为虚拟主机设置这些属性。

如需配置出站 TLS/SSL 的完整说明,请参阅配置从边缘到后端(Cloud 和私有云)的 TLS

TargetServer 架构

请参阅 GitHub 上的 TargetServer 和其他实体的架构。

运行状况监控

借助运行状况监控,您可以主动轮询 TargetServer 配置中定义的后端服务网址,以增强负载平衡配置。启用运行状况监控功能后,当 HealthMonitor 确定 TargetServer 处于活动状态时,发生故障的 TargetServer 将会自动重新置于轮替中。

运行状况监控与 <MaxFailures> 配合工作。如果未启用运行状况监控功能,则 <MaxFailures> 会指定从 API 代理发送到 TargetServer(它将请求重定向至另一个 TargetServer)的失败请求数量上限。然后,在您重新部署代理之前,发生故障的 TargetServer 会停止轮替。

启用运行状况监控功能后,发生故障的 TargetServer 会自动重新置于轮替中,无需重新部署代理。

HealthMonitor 可充当一个简单的客户端,通过 TCP 或 HTTP 调用后端服务:

  • TCP 客户端仅确保能够打开套接字。
  • 您可将 HTTP 客户端配置为向后端服务提交有效的 HTTP 请求。您可以定义 HTTP GET、PUT、POST 或 DELETE 操作。HTTP 监视器调用的响应必须与 <SuccessResponse> 块中配置的设置相匹配。

成功和失败

启用健康检查后,Edge 会开始向目标服务器发送健康检查健康检查是发送到目标服务器的请求,用于确定目标服务器是否健康状况良好。

健康检查可能产生两种结果:

  • 成功:如果健康检查成功,则目标服务器会被视为健康状况良好。通常,以下一项或多项原因导致此结果:
    • 目标服务器接受与指定端口的新连接,响应该端口上的请求,然后在指定的时间范围内关闭该端口。目标服务器返回的响应包含“Connection: close”字样
    • 目标服务器以 200 (OK) 或您确定可以接受的其他 HTTP 状态代码响应健康检查请求。
    • 目标服务器以与预期消息正文匹配的消息正文响应健康检查请求。

    当 Edge 确定服务器运行状况良好时,Edge 会继续或继续向其发送请求。

  • 失败:目标服务器可以通过不同的方式使健康检查失败,具体取决于检查类型。当目标服务器出现以下情况时,可以记录失败:
    • 拒绝从 Edge 到健康检查端口的连接。
    • 在指定时间段内未响应健康检查请求。
    • 返回意外的 HTTP 状态代码。
    • 回复消息正文与预期消息正文不匹配。

    如果目标服务器未通过健康检查,Edge 会递增该服务器的故障计数。如果该服务器的故障次数达到或超过预定义的阈值 (<MaxFailures>),则 Edge 会停止向该服务器发送请求。

启用 HealthMonitor

如需创建 HealthMonitor,请将 <HealthMonitor> 元素添加到代理的 TargetEndpoint 的 HTTPConnection 配置中。您不能在界面中执行此操作。而是需要创建代理配置并将其作为 ZIP 文件上传到 Edge。代理配置是 API 代理各个方面的结构化描述。代理配置包括预定义目录结构中的 XML 文件。如需了解详情,请参阅 API 代理配置参考文档

简单的 HealthMonitor 定义了 IntervalInSec 与 TCPMonitor 或 HTTPMonitor 的组合。<MaxFailures> 元素指定从 API 代理发送到 TargetServer(它将请求重定向至另一个 TargetServer)的失败请求数量上限。默认情况下,<MaxFailures> 为 0,表示 Edge 不执行任何纠正操作。配置 Health Monitor 时,请确保将 <TargetEndpoint> 标记的 <HTTPTargetConnection> 标记中的 <MaxFailures> 设置为非零值。

TCPMonitor

以下配置定义了一个 HealthMonitor,它通过每 5 秒在端口 80 上打开一个连接来轮询每个 TargetServer。(端口为可选项。如果未指定,则 TCPMonitor 端口即为 TargetServer 端口。)

  • 如果连接失败或用时超过 10 秒,则该 TargetServer 的失败计数将会加 1。
  • 如果连接成功,则 TargetServer 的失败计数将重置为 0。

您可以将 HealthMonitor 添加为 TargetEndpoint 的 HTTPTargetConnetion 元素的子元素,如下所示:

<TargetEndpoint name="default">
  <HTTPTargetConnection>
      <LoadBalancer>
        <Algorithm>RoundRobin</Algorithm>
        <Server name="target1" />
        <Server name="target2" />
        <MaxFailures>5</MaxFailures>
      </LoadBalancer>
      <Path>/test</Path>
      <HealthMonitor>
        <IsEnabled>true</IsEnabled>
        <IntervalInSec>5</IntervalInSec>
        <TCPMonitor>
            <ConnectTimeoutInSec>10</ConnectTimeoutInSec>
            <Port>80</Port>
        </TCPMonitor>
      </HealthMonitor>
  </HTTPTargetConnection>
. . .

带有 TCPMonitor 配置元素的 HealthMonitor

下表介绍了 TCPMonitor 配置元素:

名称 说明 默认 是否必需?
IsEnabled 启用或停用 HealthMonitor 的布尔值。 false
IntervalInSec 每个轮询 TCP 请求之间的时间间隔(秒)。 0
ConnectTimeoutInSec 必须建立与 TCP 端口的连接才算成功的时间。如果未能按指定的时间间隔连接,则计为失败,TargetServer 的负载均衡器失败次数加 1。 0
Port 可选。将用来建立 TCP 连接的端口。如果未指定,则 TCPMonitor 端口为 TargetServer 端口。 0

HTTPMonitor

使用 HTTPMonitor 的示例 HealthMonitor 每 5 秒向后端服务提交一次 GET 请求。以下示例将 HTTP Basic Authorization 标头添加到请求消息中。响应配置定义了要与后端服务的实际响应进行比较的设置。在以下示例中,预期响应是 HTTP 响应代码 200,以及其值为 YourOK 的自定义 HTTP 标头 ImOK。如果响应不匹配,则负载均衡器配置将请求视为失败。

HTTPMonitor 支持将后端服务配置为使用 HTTP 和单向 HTTPS 协议。但是,它不支持以下各项:

  • 双向 HTTPS(也称为双向 TLS/SSL)
  • 自签名证书

请注意,HTTP 监视器中的所有请求和响应设置将特定于必须调用的后端服务。

    <HealthMonitor>
      <IsEnabled>true</IsEnabled>
      <IntervalInSec>5</IntervalInSec>
      <HTTPMonitor>
        <Request>
          <IsSSL>true</IsSSL>
          <ConnectTimeoutInSec>10</ConnectTimeoutInSec>
          <SocketReadTimeoutInSec>30</SocketReadTimeoutInSec>
          <Port>80</Port>
          <Verb>GET</Verb>
          <Path>/healthcheck</Path>
          <Header name="Authorization">Basic 12e98yfw87etf</Header>
          <IncludeHealthCheckIdHeader>true</IncludeHealthCheckIdHeader>
        </Request>
        <SuccessResponse>
          <ResponseCode>200</ResponseCode>
          <Header name="ImOK">YourOK</Header>
        </SuccessResponse>
      </HTTPMonitor>
    </HealthMonitor>
    

带有 HTTPMonitor 配置元素的 HealthMonitor

下表介绍了 HTTPMonitor 配置元素:

名称 说明 默认 是否必需?
IsEnabled 启用或停用 HealthMonitor 的布尔值。 false
IntervalInSec 每个轮询请求之间的时间间隔(秒)。 0
Request

由 HealthMonitor 发送到轮替中的 TargetServer 的出站请求消息的配置选项。

该路径不支持变量。

不适用
IsSSL 指定是否使用 HTTPS(安全 HTTP)监控连接。

可能的值:
  • true:使用 HTTPS。
  • false:使用 HTTP。
  • 未指定:使用目标服务器配置。
false
ConnectTimeoutInSec 必须通过 TCP 连接完成与 HTTP 服务的握手才算成功的时间(秒)。如果未能按指定的时间间隔连接,则计为失败,TargetServer 的负载均衡器失败次数加 1。 0
SocketReadTimeoutInSec 必须从 HTTP 服务读取数据才算成功的时间(秒)。如果未能按指定的时间间隔读取,则计为失败,TargetServer 的负载均衡器失败次数加 1。 0
Port 用来与后端服务建立 HTTP 连接的端口。 不适用
Verb 用于向后端服务发送每个轮询 HTTP 请求的 HTTP 动词。 不适用
Path 附加到 TargetServer 中定义的网址的路径。使用路径元素在 HTTP 服务上配置“轮询端点”。 不适用

IncludeHealthCheckIdHeader

允许您跟踪上游系统上的健康检查请求。IncludeHealthCheckIdHeader 采用布尔值,默认值为 false。如果将其设置为 true,则有一个名为 X-Apigee-Healthcheck-IdHeader 会被注入到健康检查请求。该标头的值是动态分配的,格式为 ORG/ENV/SERVER_UUID/N,其中 ORG 是组织名称,ENV 是环境名称,SERVER_UUID 是用于标识 MP 的唯一 ID,N 是经过的毫秒数(自 1970 年 1 月 1 日算起)。

生成的请求标头示例:

X-Apigee-Healthcheck-Id: orgname/envname/E8C4D2EE-3A69-428A-8616-030ABDE864E0/1586802968123
false
Payload 为每个轮询 HTTP 请求生成的 HTTP 正文。请注意,GET 请求不需要此元素。 不适用
SuccessResponse 轮询的后端服务生成的入站 HTTP 响应消息的匹配选项。如果响应不匹配,则失败次数会加 1。 不适用
ResponseCode 应从轮询的 TargetServer 接收的 HTTP 响应代码。代码与指定的代码不同会导致失败,且轮询后端服务的计数将加 1。您可以定义多个 ResponseCode 元素。 不适用
Headers 应从轮询的后端服务接收的一个或多个 HTTP 标头和值的列表。如果响应中的任何 HTTP 标头或值与指定值不同,都将导致失败,并且轮询 TargetServer 的计数将增加 1。您可以定义多个标头元素。 不适用