envoy重试_具有Envoy代理的微服务模式,第二部分:超时和重试

envoy重试

该博客是系列文章的一部分,该系列文章更深入地介绍了Envoy ProxyIstio.io ,以及它如何实现一种更优雅的连接和管理微服务的方式。 跟随我@christianposta ,紧跟这些博客文章的发布。

这是接下来几部分的想法(将在发布时更新链接):

  • 断路器(第一部分)
  • 重试/超时(第二部分)
  • 分布式跟踪(第三部分)
  • 普罗米修斯的度量标准收集(第四部分)
  • 服务发现(第五部分)
  • 接下来的部分将介绍更多的客户端功能(请求阴影,TLS等),只是不确定哪些部分将是:)

第二部分– Envoy代理的超时和重试

第一篇博客文章向您介绍了Envoy Proxy的断路功能实现 。 在第二部分中,我们将仔细研究如何启用额外的弹性功能,例如超时和重试。 这些演示有意简单,因此我可以分别说明模式和用法。 请下载此演示的源代码,然后继续!

该演示由客户端和服务组成。 客户端是一个Java http应用程序,它模拟对“上游”服务进行http调用(请注意,我们在这里使用Envoys术语,并且贯穿此repo )。 客户端打包在名为docker.io/ceposta/http-envoy-client:latest的Docker映像中。 http-client Java应用程序旁边是Envoy Proxy的实例。 在此部署模型中,Envoy与服务(在本例中为http客户端)一起作为边车进行了部署。 当http客户端发出出站呼叫(到“上游”服务)时,所有呼叫都通过Envoy代理端进行。

这些示例的“上游”服务是httpbin.org 。 httpbin.org允许我们轻松模拟HTTP服务行为。 太棒了,所以如果您没有看过,请检查一下。

retriestimeouts演示都有自己的 envoy.json配置文件。 我绝对建议您查看配置文件各部分参考文档,以帮助您了解完整的配置。 datawire.io的好伙伴为Envoy及其配置提供了不错的介绍 ,您也应该查看一下。

运行重试演示

对于重试演示,我们将在Envoy中配置路由,如下所示:

"routes": [
    {
      "timeout_ms": 0,
      "prefix": "/",
      "auto_host_rewrite": true,
      "cluster": "httpbin_service",
      "retry_policy": {
        "retry_on": "5xx",
        "num_retries": 3
      }

    }

在这里,我们说要对5xx的HTTP状态最多重试3次。

如果您已经运行了先前的演示,请确保对此(或任何)演示重新开始。 对于每个演示,我们都有不同的Envoy配置,并希望确保每次都从干净的开始。

首先停止任何现有的演示:

./docker-stop.sh

现在让我们进行retries演示:

./docker-run.sh -d retries

现在,让我们行使客户端通过一个调用,这将创下一个HTTP端点应返回一个HTTP 500错误。 我们将使用curl.sh脚本,该脚本设置为在演示容器内调用curl。

./curl.sh -vvvv localhost:15001/status/500

我们应该看到这样的东西:

* Hostname was NOT found in DNS cache
*   Trying ::1...
* connect to ::1 port 15001 failed: Connection refused
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 15001 (#0)
> GET /status/500 HTTP/1.1
> User-Agent: curl/7.35.0
> Host: localhost:15001
> Accept: */*
> 
< HTTP/1.1 500 Internal Server Error
* Server envoy is not blacklisted
< server: envoy
< date: Thu, 25 May 2017 05:55:37 GMT
< content-type: text/html; charset=utf-8
< access-control-allow-origin: *
< access-control-allow-credentials: true
< x-powered-by: Flask
< x-processed-time: 0.000718116760254
< content-length: 0
< via: 1.1 vegur
< x-envoy-upstream-service-time: 684
< 
* Connection #0 to host localhost left intact

大! 现在,让我们检查Envoy为我们做了什么:

./get-envoy-stats.sh | grep retry
cluster.httpbin_service.retry.upstream_rq_500: 3
cluster.httpbin_service.retry.upstream_rq_5xx: 3
cluster.httpbin_service.upstream_rq_retry: 3
cluster.httpbin_service.upstream_rq_retry_overflow: 0
cluster.httpbin_service.upstream_rq_retry_success: 0

好极了! 我们在这里看到,由于HTTP 500错误,特使已重试了3次。

如果天真的处理,重试会对您的服务体系结构产生有害影响。 它们可以帮助传播故障或对可能陷入困境的内部服务造成DDoS类型的攻击。

重试时要注意以下几点:

  • Envoy会自动进行带抖动的指数重试。 有关更多信息,请参阅文档
  • 您可以设置重试超时(每次重试超时),但是总体路由超时(已为路由表配置;请参见timeouts演示以获取确切配置);仍然可以设置/应用; 这是为了短路任何失控重试/指数补偿
  • 当您可能有大量连接时,应始终设置断路器重试配置以限制重试的配额数量。 请参阅Envoy文档中断路器有效重试部分

运行超时演示

对于超时演示,我们将在Envoy中配置路由,如下所示:

"routes": [
    {
      "timeout_ms": 0,
      "prefix": "/",
      "auto_host_rewrite": true,
      "cluster": "httpbin_service",
      "timeout_ms": 3000
    }

此配置为通过此路由到达httpbin_service集群的所有呼叫设置了全局(即包括所有重试)3s超时。

每当处理超时时,我们都必须了解源自边缘的请求的整体全局超时。 我们会发现自己非常难以调试,因为随着我们对网络调用图的深入了解,超时不会逐渐减少。 换句话说,当您浏览调用图时,在调用图中更深的服务调用的服务超时应小于先前服务的调用:

Envoy可以帮助传播超时信息,而gRPC之类的协议可以传播deadline信息。 在继续阅读本系列文章时,我们将看到如何使用Istio Mesh控制Envoy代理,而控制平面可以帮助我们进行故障注入以发现超时异常。

如果您已经运行了先前的演示,请确保对此(或任何)演示重新开始。 对于每个演示,我们都有不同的Envoy配置,并希望确保每次都从干净的开始。

首先停止任何现有的演示:

./docker-stop.sh

现在让我们进行timeouts演示:

./docker-run.sh -d timeouts

现在,让我们行使客户端通过一个调用,这将创下一个HTTP端点应该推迟了大约5秒的响应。 此延迟应足以触发使节超时。 我们将使用curl.sh脚本,该脚本设置为在演示容器内调用curl。

./curl.sh -vvvv localhost:15001/delay/5

我们应该看到类似以下的输出:

* Hostname was NOT found in DNS cache
*   Trying ::1...
* connect to ::1 port 15001 failed: Connection refused
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 15001 (#0)
> GET /delay/5 HTTP/1.1
> User-Agent: curl/7.35.0
> Host: localhost:15001
> Accept: */*
> 
< HTTP/1.1 504 Gateway Timeout
< content-length: 24
< content-type: text/plain
< date: Thu, 25 May 2017 06:13:53 GMT
* Server envoy is not blacklisted
< server: envoy
< 
* Connection #0 to host localhost left intact
upstream request timeout

我们看到我们的请求已超时!

让我们检查Envoy的统计信息:

./get-envoy-stats.sh | grep timeout

在这里,我们看到1个请求(我们发送的那个!)被Envoy超时了。

cluster.httpbin_service.upstream_cx_connect_timeout: 0
cluster.httpbin_service.upstream_rq_per_try_timeout: 0
cluster.httpbin_service.upstream_rq_timeout: 1
http.admin.downstream_cx_idle_timeout: 0
http.egress_http.downstream_cx_idle_timeout: 0

如果我们以较小的延迟这次发送请求,则应该看到该呼叫通过:

./curl.sh -vvvv localhost:15001/delay/2
* Hostname was NOT found in DNS cache
*   Trying ::1...
* connect to ::1 port 15001 failed: Connection refused
*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 15001 (#0)
> GET /delay/2 HTTP/1.1
> User-Agent: curl/7.35.0
> Host: localhost:15001
> Accept: */*
> 
< HTTP/1.1 200 OK
* Server envoy is not blacklisted
< server: envoy
< date: Thu, 25 May 2017 06:15:41 GMT
< content-type: application/json
< access-control-allow-origin: *
< access-control-allow-credentials: true
< x-powered-by: Flask
< x-processed-time: 2.00246119499
< content-length: 309
< via: 1.1 vegur
< x-envoy-upstream-service-time: 2145
< 
{
  "args": {}, 
  "data": "", 
  "files": {}, 
  "form": {}, 
  "headers": {
    "Accept": "*/*", 
    "Connection": "close", 
    "Host": "httpbin.org", 
    "User-Agent": "curl/7.35.0", 
    "X-Envoy-Expected-Rq-Timeout-Ms": "3000"
  }, 
  "origin": "68.3.84.124", 
  "url": "http://httpbin.org/delay/2"
}
* Connection #0 to host localhost left intact

还要注意,Envoy传播超时头,以便上游服务对预期的情况有所了解。

系列

继续关注 ! 第三部分跟踪应该很快着陆!

翻译自: https://www.javacodegeeks.com/2017/05/microservices-patterns-envoy-proxy-part-ii-timeouts-retries.html

envoy重试

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值