资讯详情

负载均衡 容错 熔断 限流和降级

3. 负载均衡

为了确保高可用性,每个微服务都需要部署多个服务实例来提供服务。此时,客户端服务的负载平衡。

3.1 常见的负载平衡策略 3.1.1 随机 将来自网络的请求随机分配给内部的多个服务器。

3.1.2 轮询 每一个来自网络中的请求,轮流分配给内部的服务器,从1到N然后重新开始。此种负载均衡算法适合服务器组内部的服务器都具有相同的配置并且平均服务请求相对均衡的情况。

3.1.3 加权轮询 根据服务器的不同处理能力,将不同的权值分配给每个服务器,以接受相应权值的服务请求。例如,服务器A的权值设计为1,B的权值是3,C如果服务器的权值为6,则服务器的权值为6A、B、C接收10%、30%、60%的服务请求。这种平衡算法可以保证高性能服务器的利用率更高,避免低性能服务器过载。

3.1.4 IP Hash 这样生成请求源IP哈希值,并通过这个哈希值找到正确的真实服务器。这意味着他对应的服务器对同一主机总是一样的。这样,你就不需要保存任何来源IP。但需要注意的是,这种方法可能会导致服务器负载不平衡。

3.1.5 最少连接数 客户端的每个请求服务在服务器上的停留时间可能会有很大的差异。随着工作时间的延长,如果采用简单的循环或随机平衡算法,每个服务器上的连接过程可能会有很大的差异,没有达到真正的负载平衡。至少连接数平衡算法有一个数据记录每个服务器据记录,记录当前服务器处理的连接数量,当有新的服务连接请求时,将当前请求分配给连接数最少的服务器,使平衡更符合实际情况,负载更平衡。该均衡算法适用于长期处理的请求服务,如FTP。

4. 容错

容错,这个词的理解,直接意味着你可以容忍错误,不要让错误再次扩大,让错误的影响在一个固定的边界内,数千英里的堤坝被蚂蚁摧毁我们使用容错的方式是让蚂蚁不变大。所以我们常见的降级、流量限制、保险丝、加班等都是容错的方法。

在呼叫服务集群时,如果微服务呼叫异常,如加班、连接异常、网络异常等,则根据容错策略进行服务容错。目前支持的服务容错策略有快速故障和故障切换。如果连续失败多次,则直接熔断,不再启动呼叫。这可以避免异常的服务拖累所有依赖他的服务。

4.1 容错策略 4.1.1 快速失败 服务只发起一次待用,失败立即报错。通常用于非幂等下性写作操作

4.1.2 失效切换 服务发起调用,当出现失败后,重试其他服务器。通常用于读操作,但重试会带来更长时间的延迟。重试的次数通常是可以设置的

4.1.3 失败安全 失败安全, 服务调用异常时,直接忽略。通常用于日志等操作。

4.1.4 自动恢复失败 服务调用异常时,记录失败请求,定期重发。通常用于消息通知。

4.1.5 forking Cluster 并行调用多个服务器,只要有一个成功,即返回。通常用于实时读取操作。可以通过forks=n设置最大并行数。

4.1.6 广播调用 广播调用所有提供商,逐一调用,任何失败都失败。通常用于通知所有提供商更新缓存或日志等本地资源信息。

5. 熔断

熔断技术可以说是一种智能容错。当调用以满足失败次数时,失败比例会触发熔断器打开,当前程序会自动切断RPC调用,防止错误进一步扩大。熔断器的实现主要考虑三种模式:关闭、打开和半开。各状态的转换如下图所示。

当我们处理异常时,我们应该根据具体的业务情况来确定处理方法。例如,当我们呼叫商品接口时,另一方只是暂时降级,因此作为一个网关呼叫,我们应该切断可替代的服务来执行或获取基础数据,并给用户一个友好的提示。还需要区分异常类型,比如依赖服务崩溃,可能需要很长时间才能解决。也可能是因为服务器负载临时过高。熔断器应能够根据具体的错误类型来识别这种异常类型。增加手动设置,当服务恢复时间不确定时,管理员可以手动强制切换熔断状态。最后,熔断器的使用场景是调用可能失败的远程服务程序或共享资源。本地私有资源如果在本地缓存,使用熔断器会增加系统的额外费用。还应注意,熔断器不能作为应用程序中业务逻辑异常处理的替代品。

有些异常顽固,突然发生,不可预测,难以恢复,也会导致联盟失败(例如,假设服务集群的负荷非常高,如果集群的一部分在这个时候挂断,但也占据了大部分资源,整个集群可能会遭受痛苦)。如果我们在这个时候继续重试,结果大多是失败的。因此,我们的应用程序需要立即进入失败状态(fast-fail),并采取适当的恢复方法。

我们可以用状态机来实现CircuitBreaker,它有三种状态:

关闭( Closed ):默认情况下Circuit Breaker是关闭的,此时允许操作执行。CircuitBreaker内部记录了最近失败的次数,如果相应的操作失败,次数将继续一次。若在一定时间内,失败次数(或失败率)达到阈值,CircuitBreaker会转换到开启( Open )状态。在开启状态下,Circuit Breaker该计时器的目的是给集群相应的时间来恢复故障。计时器时间到了,CircuitBreaker它将转换为半开( Half-Open )状态。

开启( Open ):在这种状态下,相应的操作将立即失败,并立即抛出异常。

半开启( Half-Open ):在这种状态下,Circuit Breaker会允许执行一定数量的操作。若所有操作都成功,CircuitBreaker假设故障已经恢复,它将转换为关闭状态,并重置失败次数。如果其中 任意一次 操作失败,Circuit Breaker它会认为故障仍然存在,因此它将转换为打开状态并再次打开计时器(给系统一些时间从失败中恢复)

6. 限流和降级

确保核心服务的稳定性。为了确保核心服务的稳定性,随着访问量的增加,需要为系统可处理的服务数量设置极限阀值,并直接拒绝超过该阀值的要求。同时,为了确保核心服务的可用性,可以降级一些非核心服务,限制服务的最大访问量,通过管理控制台手动降级单个微服务

7. SLA

SLA:Service-LevelAgreement缩写是指服务等级协议。 是网络服务供应商与客户之间的合同,定义了服务类型、服务质量、客户支付等术语。 典型的SLA包括以下项目:

最小带宽分配给客户;

客户带宽极限;

能同时服务的客户数量;

通知安排可能影响用户行为的网络变化;

访问可用性拨入;

运用统计学;

99.9%有效工作时间或每天最多停机1分钟;

各类客户的流量优先;

客户技术支持和服务;

为服务供应商不能满足处罚规定 SLA需求指定。

8. API网关

这里提到的网关是指API面对网关意味着把一切都放在一边API调用统一接入API网关层,有统一的网关层访问和输出。网关的基本功能包括:统一访问、安全保护、协议适应、流量控制、长度链接支持、容错能力。有了网关,每个API服务团队可以专注于自己的业务逻辑处理,API网关更注安全、流量、路由等问题。

9. 多级缓存

最简单的缓存是检查数据库,然后将数据写入缓存中,例如redis并设置过期时间。由于过期失效,应注意缓存穿透率的计算公式,如查询方法queryOrder(1000/1s)嵌套查询DB方法queryProductFromDb(300//s),那么redis穿透率为300/1000,在这种缓存方式下,要注意穿透率,穿透率高说明缓存效果不好。使用缓存的另一种方法是持久缓存,即不设置过期时间,这将面临数据更新的问题。使用缓存的另一种方法是持久缓存,即不设置过期时间,这将面临数据更新的问题。一般有两种方法,一种是使用时间戳,默认查询redis主要是每次设置数据时放一个时间戳。每次读取数据时,将系统当前时间与上次设置的时间戳进行比较。例如,如果超过5分钟,请再次查看数据库。这样可以保证redis里面总有数据,一般是对的DB一种容错方法。另一个是真正的让步redis做为DB使用。图中画的是通过订阅数据库绘制的binlog数据通过数据异构系统推送到缓存,并将缓存设置为多级。可使用jvmcache作为应用中的一级缓存,它通常体积小,访问频率高,更适合这种缓存jvmcache方式,一套redis作为二级remote此外,最外层的三级缓存redis作为持久缓存。

10. 超时和重试

加班和重试机制也是一种容错的方法。RPC调用的地方,如阅读redis,db,mq等等,由于网络故障或所依赖的服务故障,长时间不能返回结果,会导致线程增加,增加cpu负荷,甚至导致雪崩。所以对每一个RPC调用应设置超时时间。对于强依赖RPC调用资源时,应有重试机制,但建议重试1-2次。此外,如果有重试,则应相应减少超时时间。例如,如果重试1次,则共调用2次。如果超时配置是2s,然后客户端会等4s才能返回。因此重试 加班方式,加班时间要调小。这里再谈一次PRC调用时间消耗在哪些环节?正常调用统计的耗时主要包括: ①调用端RPC框架执行时间 ②网络发送时间 ③服务端RPC框架执行时间 ④服务器业务代码时间。调用方和服务方都有自己的性能监控,如调用方tp99是500ms,服务方tp99是100ms,找网络组的同事确认网络没有问题。那么时间花在哪里呢?客户端调用方有两个原因,另一个原因是网络TCP重传。所以要注意这两个。

11. 线程池隔离

在抗量这个环节,Servlet3异步的时候,有提到过线程隔离。线程隔离的之间优势就是防止级联故障,甚至是雪崩。当网关调用N多个接口服务的时候,我们要对每个接口进行线程隔离。比如,我们有调用订单、商品、用户。那么订单的业务不能够影响到商品和用户的请求处理。如果不做线程隔离,当访问订单服务出现网络故障导致延时,线程积压最终导致整个服务CPU负载满。就是我们说的服务全部不可用了,有多少机器都会被此刻的请求塞满。那么有了线程隔离就会使得我们的网关能保证局部问题不会影响全局。

12. 降级和限流

关于降级限流的方法业界都已经有很成熟的方法了,比如FAILBACK机制,限流的方法令牌桶,漏桶,信号量等。这里谈一下我们的一些经验,降级一般都是由统一配置中心的降级开关来实现的,那么当有很多个接口来自同一个提供方,这个提供方的系统或这机器所在机房网络出现了问题,我们就要有一个统一的降级开关,不然就要一个接口一个接口的来降级。也就是要对业务类型有一个大闸刀。还有就是 降级切记暴力降级,什么是暴力降级的,比如把论坛功能降调,结果用户显示一个大白板,我们要实现缓存住一些数据,也就是有托底数据。限流一般分为分布式限流和单机限流,如果实现分布式限流的话就要一个公共的后端存储服务比如redis,在大nginx节点上利用lua读取redis配置信息。我们现在的限流都是单机限流,并没有实施分布式限流。

13. 网关监控和统计

API网关是一个串行的调用,那么每一步发生的异常要记录下来,统一存储到一个地方比如elasticserach中,便于后续对调用异常的分析。鉴于公司docker申请都是统一分配,而且分配之前docker上已经存在3个agent了,不再允许增加。我们自己实现了一个agent程序,来负责采集服务器上面的日志输出,然后发送到kafka集群,再消费到elasticserach中,通过web查询。现在做的追踪功能还比较简单,这块还需要继续丰富。

标签: 变送器负载

锐单商城拥有海量元器件数据手册IC替代型号,打造 电子元器件IC百科大全!

锐单商城 - 一站式电子元器件采购平台