1.6 使用微服务引擎功能
1.6.3 使用服务治理
1.6.3.3 基于动态配置的流量特征治理开发
微服务引擎提供了简单易用的基于流量标记治理的能力。您可以通过微服务引擎的服 务治理功能定义业务特征和治理规则,也可以通过动态配置管理配置项的方式下发治 理规则,详情请参考治理微服务。
本章节重点介绍和代码开发有关的内容,包括如何配置依赖、涉及的配置项,以及不 同微服务开发框架对于流量特征治理支持的差异的内容。
Java Chassis
Java Chassis通过Handler实现了基于流量标记治理能力。其中Provider实现了限流、
熔断和隔离仓,Consumer实现了重试。
1. 使用流量标记治理能力,首先需要在代码中引入依赖:
<dependency>
<groupId>org.apache.servicecomb</groupId>
<artifactId>handler-governance</artifactId>
</dependency>
2. 然后配置Handler链:
servicecomb:
handler:
chain:
Consumer:
default: governance-consumer,loadbalance Provider:
default: governance-provider
Java Chassis是基于Open API的REST/RPC框架,在模型上和单纯的REST框架存在差 异。Java Chassis提供两种模式匹配规则,第一种是基于REST的,第二种是基于RPC 的。可以通过配置项:servicecomb.governance.{operation}.matchType 指定匹配规 则,默认使用REST。如果使用Java Chassis中的highway协议调用,需要指定
matchType类型为rpc。比如:
servicecomb:
governance:
matchType: rest # 设置全局默认是rest匹配模式,highway协议设置为rpc GovernanceEndpoint.helloRpc:
matchType: rpc # 设置服务端的接口helloRpc采用RPC匹配模式 在REST匹配模式下, apiPath使用url, 比如:
servicecomb:
matchGroup:
userLoginAction: | matches:
- apiPath:
exact: "/user/login"
在RPC匹配模式下, apiPath使用operation, 比如:
servicecomb:
matchGroup:
userLoginAction: |
Spring Cloud
Spring Cloud通过Aspect拦截RequestMappingHandlerAdater实现了限流、熔断和隔 离仓,通过拦截RestTemplate和FeignClient实现了重试。
使用流量标记治理能力,首先需要在代码中引入依赖:
<dependency>
<groupId>com.huaweicloud</groupId>
<artifactId>spring-cloud-starter-huawei-governance</artifactId>
</dependency>
Spring Cloud是基于REST的框架,能比较好的符合流量特征治理的匹配语义,apiPath 和headers分别对应HTTP协议的概念:
servicecomb:
matchGroup:
userLoginAction: |
matches:
- apiPath:
exact: "/user/login"
method:
- POST - headers:
Authentication:
prefix: Basic
Dubbo
Dubbo的Provider通过Filter拦截请求实现了限流、熔断和隔离仓,通过拦截 ClusterInvoker实现了重试。
使用流量标记治理能力,首先需要在代码中引入依赖:
<dependency>
<groupId>com.huaweicloud.dubbo-servicecomb</groupId>
<artifactId>dubbo-servicecomb-governance-center</artifactId>
<version>${project.version}</version>
</dependency>
如果要使用重试,需要修改Dubbo的Spring配置文件,将Dubbo默认的ClusterInvoker 修改为dubbo-servicecomb:
<dubbo:consumer cluster="dubbo-servicecomb"></dubbo:consumer>
Dubbo是一个RPC框架,需要定义operation和apiPath的映射关系,比如,服务端限 流、熔断、隔离仓场景:com.huaweicloud.it.order.OrderGovernanceService.hello;
客户端重试场景:com.huaweicloud.it.order.OrderGovernanceService.retry。headers 使用Attachments,需要包含在Attachments里面的头才会参与匹配。
servicecomb:
matchGroup:
userLoginAction: | matches:
- apiPath:
exact: "com.huaweicloud.it.order.OrderGovernanceService.hello"
method:
- POST - headers:
Authentication:
prefix: Basic
自定义
服务治理的默认实现并不一定能够解决业务的所有问题。自定义治理功能可以方便的 在不同的场景下使用基于流量的治理能力,比如在网关场景下进行流控,在Java Chassis场景下支持URL匹配等。SDK基于Spring,使用Spring的框架都能够灵活的使用 这些API,方法类似。
下面以流控为例,说明如何使用API。使用API开发的自定义代码,也可以通过微服务 引擎的管理控制台下发业务和治理规则。
代码的基本过程包括声明RateLimitingHandler的引用,创建GovernanceRequest,拦 截(包装)业务逻辑,处理治理异常。
@Autowired
private RateLimitingHandler rateLimitingHandler;
GovernanceRequest governanceRequest = convert(request);
CheckedFunction0<Object> next = pjp::proceed;
DecorateCheckedSupplier<Object> dcs = Decorators.ofCheckedSupplier(next);
try {
SpringCloudInvocationContext.setInvocationContext();
RateLimiter rateLimiter = rateLimitingHandler.getActuator(request);
if (rateLimiter != null) {
dcs.withRateLimiter(rateLimiter);
}
return dcs.get();
} catch (Throwable th) {
if (th instanceof RequestNotPermitted) { response.setStatus(429);
response.getWriter().print("rate limited.");
LOGGER.warn("the request is rate limit by policy : {}", th.getMessage());
} else {
if (serverRecoverPolicy != null) { return serverRecoverPolicy.apply(th);
}
throw th;
}} finally {
SpringCloudInvocationContext.removeInvocationContext();
}
上面简单的介绍了自定义开发。对于更加深入的使用方式,也可以直接参考Java Chassis、Spring Cloud、Dubbo项目中的默认实现代码。