Springcloudgateway详解和配置使⽤
spring cloud gateway 介绍
1. ⽹关是怎么演化来的
单体应⽤拆分成多个服务后,对外需要⼀个统⼀⼊⼝,解耦客户端与内部服务
2. ⽹关的基本功能
⽹关核⼼功能是路由转发,因此不要有耗时操作在⽹关上处理,让请求快速转发到后端服务上
⽹关还能做统⼀的熔断、限流、认证、⽇志监控等
可以和服务注册中⼼完美的整合,如:Eureka、Consul、Nacos
3.关于Spring Cloud Gateway
在SpringCloud微服务体系中,有个很重要的组件就是⽹关,在1.x版本中都是采⽤的Zuul⽹关;但在2.x版本中,zuul的升级⼀直跳
票,SpringCloud最后⾃⼰研发了⼀个⽹关替代Zuul,那就是SpringCloud Gateway
⽹上很多地⽅都说Zuul是阻塞的,Gateway是⾮阻塞的,这么说是不严谨的,准确的讲Zuul1.x是阻塞的,⽽在2.x的版本中,Zuul也是基于Netty,也是⾮阻塞的,如果⼀定要说性能,其实这个真没多⼤差距。
⽽官⽅出过⼀个测试项⽬,创建了⼀个benchmark的测试项⽬:spring-cloud-gateway-bench,其中对⽐了:
Spring Cloud Gateway
Zuul1.x
Linkerd
Proxy Avg Latency Avg Req/Sec/Thread
gateway 6.61ms 3.24k
linkered 7.62ms 2.82k
zuul 12.56ms 2.09k
none 2.09ms 11.77k
还有⼀点就是Gateway是基于WebFlux的。这⾥引出了WebFlux名词,那什么是WebFlux?
WebFlux 介绍
左侧是传统的基于Servlet的Spring Web MVC框架,
传统的Web框架,⽐如说:struts2,springmvc等都是基于Servlet API与Servlet容器基础之上运⾏的,在Servlet3.1之后才有了异步⾮阻塞的⽀持。
右侧是5.0版本新引⼊的基于Reactive Streams的Spring WebFlux框架,从上到下依次是Router Functions,WebFlux,Reactive Streams三个新组件。
Router Functions: 对标@Controller,@RequestMapping等标准的Spring MVC注解,提供⼀套函数式风格的API,⽤于创建Router,Handler和Filter。
WebFlux: 核⼼组件,协调上下游各个组件提供响应式编程⽀持。
Reactive Streams: ⼀种⽀持背压(Backpressure)的异步数据流处理标准,主流实现有RxJava和Reactor,Spring WebFlux默认集成的是Reactor。
在Web容器的选择上,Spring WebFlux既⽀持像Tomcat,Jetty这样的的传统容器(前提是⽀持Servlet 3.1 Non-Blocking IO API),⼜⽀持像Netty,Undertow那样的异步容器。不管是何种容器,Spring WebFlux都会将其输⼊输出流适配成Flux<DataBuffer>格式,以便进⾏统⼀处理。
值得⼀提的是,除了新的Router Functions接⼝,Spring WebFlux同时⽀持使⽤⽼的Spring MVC注解声明Reactive Controller。和传统的MVC Controller不同,Reactive Controller操作的是⾮阻塞的Serve
rHttpRequest和ServerHttpResponse,⽽不再是Spring MVC⾥的HttpServletRequest和HttpServletResponse。
根据官⽅的说法,webflux主要在如下两⽅⾯体现出独有的优势:
1)⾮阻塞式
其实在servlet3.1提供了⾮阻塞的API,WebFlux提供了⼀种⽐其更完美的解决⽅案。使⽤⾮阻塞的⽅式可以利⽤较⼩的线程或硬件资源来处理并发进⽽提⾼其可伸缩性
2) 函数式编程端点
⽼⽣常谈的编程⽅式了,Spring5必须让你使⽤java8,那么函数式编程就是java8重要的特点之⼀,⽽WebFlux⽀持函数式编程来定义路由端点处理请求。
IO模式和IO多路复⽤(阻塞IO、⾮阻塞IO、同步IO、异步IO等概念)这⾥就不在阐述,因为不在本分享范围之内!
4.Spring Cloud Gateway 功能特征
基于Spring Framework 5, Project Reactor 和 Spring Boot 2.0 进⾏构建;
动态路由:能够匹配任何请求属性;
集成 Spring Cloud 服务发现功能;
可以对路由指定 Predicate(断⾔)和 Filter(过滤器);
易于编写的 Predicate(断⾔)和 Filter(过滤器);
集成Hystrix的断路器功能;
请求限流功能;
⽀持路径重写。
上图中是核⼼的流程图,最主要的就是Route、Predicates 和 Filters 作⽤于特定路由。
1)Route:**路由是⽹关的基本构件**。它由ID、⽬标URI、谓词集合和过滤器集合定义。如果聚合谓词为真,则匹配路由。
2)Predicate:**参照Java8的新特性Predicate**。这允许开发⼈员匹配HTTP请求中的任何内容,⽐如头或参数。
3)Filter:可以在发送下游请求之前或之后修改请求和响应。
我们为什么选择Gateway?
⼀⽅⾯因为Zuul已经进⼊了维护阶段,⽽且Gateway是SpringCloud团队研发的,是亲⼉⼦产品,值得信赖。⽽且很多功能Zuul都没有;⽤起来也⾮常的简单便捷。
Gateway是基于异步⾮阻塞模型上进⾏开发的,性能⽅⾯不需要担⼼。虽然Netflix 早就发布了最新的 Zuul 2.x,但 Spring Cloud 貌似没有整合计划。⽽且Netflix相关组件都宣布进⼊维护期;不知前景如何?
多⽅⾯综合考虑Gateway是很理想的⽹关选择。
Spring Cloud Gateway ⼯作原理
客户端向 Spring Cloud Gateway 发出请求。然后在 Gateway Handler Mapping 中到与请求相匹配的路由,将其发送到 Gateway Web Handler。Handler 再通过指 定的过滤器链来将请求发送到我们实
际的服务执⾏业务逻辑,然后返回。过滤器之间⽤虚线分开是因为过滤器可能会在发送代理请求之前(“pre”)或之后(“post”)执⾏业务逻辑。
Filter在“pre”类型的过滤器可以做参数校验、权限校验、流量监控、⽇志输出、协议转换等,
nginx和网关怎么配合使用在“post”类型的过滤器中可以做响应内容、响应头的修改,⽇志的输出,流量监控等有着⾮常重要的作⽤。
核⼼逻辑就是路由转发,执⾏过滤器链。
在上⾯的处理过程中,有⼀个重要的点就是讲请求和路由进⾏匹配,这时候就需要⽤到predicate,它是决定了⼀个请求⾛哪⼀个路由。
5.predicate简介
Predicate来⾃于java8的接⼝。Predicate接受⼀个输⼊参数,返回⼀个布尔值结果。该接⼝包含多种默认⽅法来将Predicate组合成其他复杂的逻辑(⽐如:与,或,⾮)。可以⽤于接⼝请求参数校验、判断新⽼数据是否有变化需要进⾏更新操作。add--与、or--或、negate--⾮。
Spring Cloud Gateway内置了许多Predict,这些Predict的源码在org.springframework.cloud.gateway.
handler.predicate包中,有兴趣可以阅读⼀下。现在列举各种Predicate如下图:
在上图中,有很多类型的Predicate,⽐如说时间类型的Predicated(AfterRoutePredicateFactory BeforeRoutePredicateFactory BetweenRoutePredicateFactory),当只有满⾜特定时间要求的请求会进⼊到此predicate中,并交由router处理;cookie类型的CookieRoutePredicateFactory,指定的cookie满⾜正则匹配,才会进⼊此router;以及host、method、path、querparam、remoteaddr类型的predicate,每⼀种predicate都会对当前的客户端请求进⾏判断,是否满⾜当前的要求,如果满⾜则交给当前请求处理。如果有很多个Predicate,并且⼀个请求满⾜多个Predicate,则按照配置的顺序第⼀个⽣效。
1. After Route Predicate Factory
After Route Predicate Factory使⽤的是时间作为匹配规则,只要当前时间⼤于设定时间,路由才会匹配请求。 l:
2. Before Route Predicate Factory
Before Route Predicate Factory也是使⽤时间作为匹配规则,只要当前时间⼩于设定时间,路由才会匹配请求。 l:
3. Between Route Predicate Factory
Between Route Predicate Factory也是使⽤两个时间作为匹配规则,只要当前时间⼤于第⼀个设定时间,并⼩于第⼆个设定时间,路由才会匹配请求。
4. Cookie Route Predicate Factory
Cookie Route Predicate Factory使⽤的是cookie名字和正则表达式的value作为两个输⼊参数,请求的cookie需要匹配cookie名和符合其中value的正则。 l:
5. Header Route Predicate Factory
Header Route Predicate Factory,与Cookie Route Predicate Factory类似,也是两个参数,⼀个header的name,⼀个是正则匹配的value。 l:
6. Host Route Predicate Factory
Host Route Predicate Factory使⽤的是host的列表作为参数,host使⽤Ant style匹配。 l:
7. Method Route Predicate Factory
Method Route Predicate Factory是通过HTTP的method来匹配路由。 l:
8. Path Route Predicate Factory
Path Route Predicate Factory使⽤的是path列表作为参数,使⽤Spring的PathMatcher匹配path,可以设置可选变量。
PathMatchInfo variables = Attribute(URI_TEMPLATE_VARIABLES_ATTRIBUTE);
Map<String, String> uriVariables = UriVariables();
String segment = ("segment");
在后续的GatewayFilter Factories就可以做对应的操作了。
9. Query Route Predicate Factory
Query Route Predicate Factory可以通过⼀个或两个参数来匹配路由,⼀个是查询的name,⼀个是查询的正则value。
10. RemoteAddr Route Predicate Factory
RemoteAddr Route Predicate Factory通过⽆类别域间路由(IPv4 or IPv6)列表匹配路由。 l:
10.1 Modifying the way remote addresses are resolved
RemoteAddr Route Predicate Factory默认情况下,使⽤的是请求的remote address。但是如果Spring Cloud Gateway是部署在其他的代理后⾯的,如Nginx,则Spring Cloud Gateway获取请求的remote address是其他代理的ip,⽽不是真实客户端的ip。
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论