1.架构的演变
传统架构->水平拆分->垂直拆分(最早的分布式)->soa(dubbo)->微服务(springCloud)
2.远程调用技术
- rpc协议:自定义数据格式,限定技术,传输速度快,效率高 tcp dubbo
- http协议:统一的数据格式,不限定技术,rest接口 tcp springCloud
什么是springCloud:
微服务架构的解决方案,是很多组件的集合.
eureka:注册中心,服务的组成与发现
zuul:网关组件,路由请求,过滤器 (包含ribbon,hystrix)
ribbon:负载均衡组件
hystrix:熔断组件
feign:远程调用组件 (包含ribbon,hystrix)
eureka:
注册中心:
demo-eureka(1.引入启动器,2配置spring.application.name=demo-eureka3.在启动类上加上@EnableEurekaServer)
客户端:
demo-provider和demo-consumer(1.引入启动器,2.配置spring.application.name eureka.client.service-url.defaultZone=http://localhost:10086/eureka 3.在启动类上添加注解@EnableDiscoveryClient)
hystrix 熔断器
降级:
1.引入hystrsix启动器
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
</dependency>
``
2.hystrsix熔断时间默认为1s,可修改
hystrix:
command:
default:
execution:
isolation:
thread:
timeoutInMillisecond: 6000 # 设置hystrix的超时时间为6000ms
``
3.在引导类上加上@EnableCircuitBreaker //开启熔断器 或者@SpringCloudApplication
4.定义熔断方法:
局部方法:@HystrixCommand(fallbackMethod = “”) 要和被熔断的方法返回值和参数列表必须一致
全局:@DefaultProperties(defaultFallback="") (返回值必须要和被熔断方法的返回值一致,参数列表必须为空)
熔断:
1.close: 闭合状态,所有请求都可以访问
2.open:打开状态,所有请求都无法访问,如果在一定时间,内容失败的比例不小于50%或者请求不小于20次
3.half open:半开状态,打开状态默认为5s的休眠期,在休眠期中,所有请求无法正常访问,过了休眠期,会进入搬开状态,让部分请求通过
hystrix:
command:
default:
circuitBreaker:
requestVolumeThreshold: 5 #触发熔断最小请求次数 默认为20
sleepWindowInMilliseconds: 4000 #休眠时长默认为5000毫秒
errorThresholdPercentage: 50 #触发熔断的失败请求最小占比 默认为50%
feign:
1.引入openfeign启动器
2.fegin.hystrix.enable=true 开启fegin的熔断功能
3.在引导类上加上@EnableFeignClients
4.创建一个借口,在接口上添加@FeignClient(value=“服务id”,fallback=实现类.class)
5.在接口中定义一些方法,这些方法与controller类似
6.创建一个熔断类,实现fegin接口,实现对应的方法,这些实现的方法就是熔断方法
zuul:
1.引入启动器
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>
2.配置:(4种路由配置)
zuul.routes.<路由名称>.url=http://localhost:8082
zuul.routes.<路由名称>.path=/xxx/**
zuul.routes.<路由名称>.serviceId=xxx #路由名称.可以随便写 习惯上服务名
zuul.routes.<路由名称>.path=/xxx/**
zuule.routes.服务名=/xxx/**
不用配置,默认就是服务id开头路径
3.在启动类上添加@EnableZuulProxy注解
zuul过滤器:
- 创建一个类继承ZuulFilter基类
- 重写四个方法
@Component
public class LoginFilter extends ZuulFilter{
@Override
public String filterType() {
// 登录校验,肯定是在前置拦截
return "pre";
}
@Override
public int filterOrder() {
// 顺序设置为1
return 1;
}
@Override
public boolean shouldFilter() {
// 返回true,代表过滤器生效。
return true;
}
@Override
public Object run() throws ZuulException {
// 登录校验逻辑。
// 1)获取Zuul提供的请求上下文对象
RequestContext ctx = RequestContext.getCurrentContext();
// 2) 从上下文中获取request对象
HttpServletRequest req = ctx.getRequest();
// 3) 从请求中获取token
String token = req.getParameter("access-token");
// 4) 判断
if(token == null || "".equals(token.trim())){
// 没有token,登录校验失败,拦截
ctx.setSendZuulResponse(false);
// 返回401状态码。也可以考虑重定向到登录页。
ctx.setResponseStatusCode(HttpStatus.UNAUTHORIZED.value());
}
// 校验通过,可以考虑把用户信息放入上下文,继续向后执行
return null;
}
}
Zuul中默认就已经集成了Ribbon负载均衡和Hystix熔断机制。但是所有的超时策略都是走的默认值,比如熔断超时时间只有1S,很容易就触发了。因此建议我们手动进行配置:
zuul:
retryable: true
ribbon:
ConnectTimeout: 250 # 连接超时时间(ms)
ReadTimeout: 2000 # 通信超时时间(ms)
OkToRetryOnAllOperations: true # 是否对所有操作重试
MaxAutoRetriesNextServer: 2 # 同一服务不同实例的重试次数
MaxAutoRetries: 1 # 同一实例的重试次数
hystrix:
command:
default:
execution:
isolation:
thread:
timeoutInMillisecond: 6000 # 熔断超时时长:6000ms