Ribbon
server.port=8081
spring.application.name=consumer-service
eureka.client.serviceUrl.defaultZone=http://localhost:1111/eureka/#ribbon,制定服务配置,默认配置类为DefaultClientConfigImpl
ribbon.ConnectTimeout=500
# 这个参数配置要小于熔断超时的配置,否则直接熔断没机会重试
ribbon.ReadTimeout=2000# 这个请求建议设置为false, 这样的话只有get请求会重试而其它类型的请求不会重试,默认为false
ribbon.OkToRetryOnAllOperations=false
#重试策略先尝试访问首选实例一次
ribbon.MaxAutoRetries=2
#尝试更换两次实例进行重试
ribbon.MaxAutoRetriesNextServer=0# 不作为eureka客户端
eureka.client.enabled=false
eureka.client.fetch-registry=false# 使用okhttp
feign.httpclient.enabled=false
feign.okhttp.enabled=true# 禁用ribbon从eureka中获取服务地址,并配置特定服务的地址
ribbon.eureka.enabled=false
hello-service.ribbon.listOfServers= http://localhost:8080,http://localhost:8082# 开启ribbon上下文的饥饿加载,默认是懒加载,第一次请求的时候才加载ribbon上下文,可以避免第一次请求超时导致熔断
ribbon.eager-load.enabled=true# 开启服务熔断
feign.hystrix.enabled=true
# 全局熔断超时时间配置,默认是1秒有点短了
hystrix.command.execution.isolation.thread.timeoutinMilliseconds=50OO
#为 hello方法单独配置超时时间,所有的hello方法都会使用这个配置
hystrix.command.hello.execution.isolation.thread.timeoutinMilliseconds=5OOO# 断路器休眠时间,默认5秒
hystrix.command.defaul七.circuitBreaker.sleepWindowinMilliseconds=20000
# 时间窗口内错误率超过这个值才断开,默认50%
hystrix.command.default.circuitBreaker.errorThresholdPercentage=90
package com.example.springcloudprovider;import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.netflix.discovery.converters.Auto;
import feign.Request;
import feign.RequestInterceptor;
import feign.RequestTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;import java.nio.charset.Charset;
import java.util.*;/*** 用于处理feign的get请求传递pojo参数的拦截器*/
@Component
public class FeignRequestInterceptor implements RequestInterceptor {@Autowiredprivate ObjectMapper objectMapper;@Overridepublic void apply(RequestTemplate template) {if (template.method().equals("GET") && template.body() != null){try {JsonNode jsonNode = objectMapper.readTree(template.body());template.body(null , Charset.defaultCharset());Map<String, Collection<String>> querys = new HashMap<>();buildQuery(jsonNode, "", querys);template.queries(querys);} catch (Exception ex){};}}private void buildQuery(JsonNode jsonNode, String path, Map<String, Collection<String>> queries) {// 叶子节点if (!jsonNode.isContainerNode()) {if (jsonNode.isNull()) {return;}Collection<String> values = queries.get(path);if (null == values) {values = new ArrayList<>();queries.put(path, values);}values.add(jsonNode.asText());return;}// 数组节点if (jsonNode.isArray()) {Iterator<JsonNode> it = jsonNode.elements();while (it.hasNext()) {buildQuery(it.next(), path, queries);}} else {Iterator<Map.Entry<String, JsonNode>> it = jsonNode.fields();while (it.hasNext()) {Map.Entry<String, JsonNode> entry = it.next();if (StringUtils.hasText(path)) {buildQuery(entry.getValue(), path + "." + entry.getKey(), queries);} else { // 根节点buildQuery(entry.getValue(), entry.getKey(), queries);}}}}}
Hystrix
原生用法
使用feign快速使用
服务降级
异常处理
工作流程
- 每次调用远程服务方法时,会先把调用逻辑包装在HystrixCommand对象中,这个command对象中包含一个断路器,每次调用完成后,Hystrix会把失败、成功、拒绝、超时等信息报告给断路器。
断路器断开的触发条件,如果10秒窗口统计信息中,该方法的QPS大于20并且错误百分比大于50%则设置短路器为打开状态,则设置断开断路器。
判断一个请求是否被允许有两个标准,第一个是断路器是否是闭合的。如果是断开的,但是断开的时间到现在已经过了一段时间了,默认是5秒,则可以允许这个请求。如果这个请求成功了,则立即闭合断路器,并重置统计数据,如果失败了则重置断路器断开时间,这样一段时间内就不会有请求进来了。
线程池划分
配置详解
优化配置
请求缓存
请求合并
线程池调整