1、网关介绍
1、为什么产生了网关
微服务架构下,随着服务的数量不断累加,当客户端访问这些微服务的时候,往往需要记住即使甚至上百个地址,这对于客户端而言,是非常复杂且难以维护的。
如果直接让客户端和各个微服务通信,存在如下问题,
- 客户端会请求多个不同的服务,需要维护不同的请求地址,增加了开发难度
- 跨域请求的问题
- 加大身份认证的难度,每个微服务需要独立认证
因此需要一种对外的统一集散地,类似于在所有服务的外层包装一个管卡,所有的请求不再是直接到服务,而实先经过网关。如此一来客户端只需要记住一个网关,比如http://oneNet.com/getorder/12
。
1、网关应用场景
除了上述优点,网关还有如下优点,
- 统一入口:未全部为服务提供一个唯一的入口,网关起到外部和内部隔离的作用,保障了后台服务的安全性。
- 鉴权校验:识别每个请求的权限,拒绝不符合要求的请求。
- 动态路由:动态的将请求路由到不同的后端集群中。
- 减少客户端与服务端的耦合:服务可以独立发展,通过网关层来做映射。
甚至:监控、负载均衡、缓存、请求分片和管理、静态响应处理。
1、流行组件
常见的API网管实现有,
基于Nginx+Lua开发, 性能高,稳定,有多个可用的插件(限流、鉴权等等)可用开箱即用。
Zuul, Netflix开源,功能丰富,使用Java开发,易于二次开发,需要运行在Web容器中,如Tomcat
Traefik,Go语言开发,轻量易用,提供大多数功能如服务路由,负载均衡等等,提供Web UI界面。
Spring Cloud Gateway,SpringCloud提供的网关服务。
基于Nginx的网关实现,Nginx是一个自由的、开源的、高性能的HTTP服务器和反向代理服务器,同时也是一个IMAP、POP3、SMTP代理服务器。
2、Spring Cloud Zuul对比Gateway
基于目前Spring cloud 支持的两种网关,Zuul和Gateway,做如下对比
1、来源
- zuul则是netflix公司的项目,只是spring将zuul集成在spring-cloud中使用而已。
- spring-cloud-Gateway是spring-cloud的一个子项目。因为zuul2.0连续跳票和zuul1的性能表现不是很理想,所以催生了spring团队开发了Gateway项目。
2、相同点
- 底层都是servlet
- 两者均是web网关,处理的是http请求
3、不同点
内部实现
- gateway对比zuul多依赖了spring-webflux,在spring的支持下,功能更强大,内部实现了限流、负载均衡等,扩展性也更强,但同时也限制了仅适合于Spring Cloud套件。
- zuul则可以扩展至其他微服务框架中,其内部没有实现限流、负载均衡等。
是否支持异步
- zuul仅支持同步
- gateway支持异步。理论上gateway则更适合于提高系统吞吐量(但不一定能有更好的性能),最终性能还需要通过严密的压测来决定
框架设计的角度
- gateway具有更好的扩展性,并且其已经发布了2.0.0的RELESE版本,稳定性也是非常好的
性能
- WebFlux 模块的名称是 spring-webflux,名称中的 Flux 来源于 Reactor 中的类 Flux。Spring webflux 有一个全新的非堵塞的函数式 Reactive Web 框架,可以用来构建异步的、非堵塞的、事件驱动的服务,在伸缩性方面表现非常好。使用非阻塞API。 Websockets得到支持,并且由于它与Spring紧密集成,所以将会是一个更好的 开发 体验。Zuul 1.x,是一个基于阻塞io的API Gateway。Zuul已经发布了Zuul 2.x,基于Netty,也是非阻塞的,支持长连接,但Spring Cloud暂时还没有整合计划。
总结:
1、总的来说,在微服务架构,如果使用了Spring Cloud生态的基础组件,则Spring Cloud Gateway相比而言更加具备优势,单从流式编程+支持异步上就足以让开发者选择它了。
2、对于小型微服务架构或是复杂架构(不仅包括微服务应用还有其他非Spring Cloud服务节点),zuul也是一个不错的选择。
3、Spring cloud Gateway
什么是Spring cloud Gateway
Spring Cloud Gateway 是 Spring Cloud 的一个全新项目,该项目是基于 Spring 5.0,Spring Boot 2.0 和 Project Reactor 等技术开发的网关,它旨在为微服务架构提供一种简单有效的统一的 API 路由管理方式。
Spring Cloud Gateway 作为 Spring Cloud 生态系统中的网关,目标是替代 Netflix Zuul,其不仅提供统一的路由方式,并且基于 Filter 链的方式提供了网关基本的功能,例如:安全,监控/指标,和限流。
术语
Route(路由):这是网关的基本构建块。它由一个 ID,一个目标 URI,一组断言和一组过滤器定义。如果断言为真,则路由匹配。
Predicate(断言):这是一个 Java 8 的 Predicate。输入类型是一个 ServerWebExchange。我们可以使用它来匹配来自 HTTP 请求的任何内容,例如 headers 或参数。
Filter(过滤器):这是org.springframework.cloud.gateway.filter.GatewayFilter的实例,我们可以使用它修改请求和响应。
原理
客户端向 Spring Cloud Gateway 发出请求。然后在 Gateway Handler Mapping 中找到与请求相匹配的路由,将其发送到 Gateway Web Handler。Handler 再通过指定的过滤器链来将请求发送到我们实际的服务执行业务逻辑,然后返回。过滤器之间用虚线分开是因为过滤器可能会在发送代理请求之前(“pre”)或之后(“post”)执行业务逻辑。
简单上手
Spring Cloud Gateway 网关路由有两种配置方式,这两种方式是等价的,建议使用 yml 方式进配置。
- 在配置文件 yml 中配置
- 通过@Bean自定义 RouteLocator,在启动主类 Application 中配置
1、加入依赖
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
2、配置文件
server:
port: 8080
spring:
application:
name: api-gateway
cloud:
gateway:
routes:
- id: gateway-service
uri: https://blog.csdn.net
predicates:
- Path=/meteor_93
//上面这段配置的意思是,配置了一个 id 为 gateway-service 的路由规则,当访问地址 http://localhost:8080/meteor_93时会自动转发到地址:http://localhost:8080/meteor_93
3、路由配置(跟配置为文件一样)
@SpringBootApplication
public class GatewayApplication {
public static void main(String[] args) {
SpringApplication.run(GatewayApplication.class, args);
}
@Bean
public RouteLocator customRouteLocator(RouteLocatorBuilder builder) {
return builder.routes()
.route("path_route", r -> r.path("/meteor_93")
.uri("https://blog.csdn.net"))
.build();
}
}
4、Predicate详解
Predicate 来源于 Java 8,是 Java 8 中引入的一个函数,Predicate 接受一个输入参数,返回一个布尔值结果。该接口包含多种默认方法来将 Predicate 组合成其他复杂的逻辑(比如:与,或,非)。可以用于接口请求参数校验、判断新老数据是否有变化需要进行更新操作。
在 Spring Cloud Gateway 中 Spring 利用 Predicate 的特性实现了各种路由匹配规则,有通过 Header、请求参数等不同的条件来进行作为条件匹配到对应的路由。网上有一张图总结了 Spring Cloud 内置的几种 Predicate 的实现。