目前常见的开源网关大致上按照语言分类有如下几类。
-
Nginx+Lua:Open Resty、Kong、Orange、Abtesting Gateway等;
-
Java:Zuul/Zuul 2、Spring Cloud Gateway、Kaazing KWG、gravitee、Dromara soul等;
-
Go:Janus、fagongzi、Grpc-Gateway;
-
.NET:Ocelot;
-
Node.js:Express Gateway、MicroGateway。
按照使用范围、成熟度等来划分,主流的有4个:OpenResty、Kong、Zuul/Zuul 2、Spring Cloud Gateway,此外fagongzi API网关最近也获得不少关注。
1. Nginx+Lua网关
OpenResty
OpenResty基于Nginx,集成了Lua语言和Lua的各种工具库、可用的第三方模块,这样我们就在Nginx既有的高效HTTP处理的基础上,同时获得了Lua提供的动态扩展能力。因此,我们可以做出各种符合我们需要的网关策略的Lua脚本,以其为基础实现网关系统。
Kong
项目地址:https://konghq.com/与https://github.com/kong/kong
Kong基于OpenResty,是一个云原生、快速、可扩展、分布式的微服务抽象层(MicroserviceAbstraction Layer),也叫API网关(API Gateway),在Service Mesh里也叫API中间件(API Middleware)。
Kong开源于2015年,核心价值在于其高性能和扩展性。从全球5000强的组织统计数据来看,Kong是现在依然在维护的、在生产环境使用最广泛的网关。
核心优势如下。
-
可扩展:可以方便地通过添加节点实现水平扩展,这意味着可以在很低的延迟下支持很大的系统负载。
-
模块化:可以通过添加新的插件来扩展Kong的能力,这些插件可以通过RESTful Admin API来安装和配置。
-
在任何基础架构上运行:Kong在任何地方都能运行,比如在云或混合环境中部署Kong,或者单个/全球的数据中心。
ABTestingGateway
项目地址:https://github.com/CNSRE/ABTestingGateway
ABTestingGateway是一个可以动态设置分流策略的网关,关注与灰度发布相关的领域,基于Nginx和ngx-lua开发,使用Redis作为分流策略数据库,可以实现动态调度功能。
ABTestingGateway是新浪微博内部的动态路由系统dygateway的一部分,目前已经开源。在以往的基于Nginx实现的灰度系统中,分流逻辑往往通过rewrite阶段的if和rewrite指令等实现,优点是性能较高,缺点是功能受限、容易出错,以及转发规则固定,只能静态分流。ABTestingGateway则采用 ngx-lua,通过启用lua-shared-dict和lua-resty-lock作为系统缓存和缓存锁,系统获得了较为接近原生Nginx转发的性能。
功能特性如下。
-
支持多种分流方式,目前包括iprange、uidrange、uid尾数和指定uid分流;
-
支持多级分流,动态设置分流策略,即时生效,无须重启;
-
可扩展性,提供了开发框架,开发者可以灵活添加新的分流方式,实现二次开发;
-
高性能,压测数据接近原生Nginx转发;
-
灰度系统配置写在Nginx配置文件中,方便管理员配置;
-
适用于多种场景:灰度发布、AB测试和负载均衡等。
据了解,美团网内部的Oceanus也是基于Nginx和ngx-lua扩展实现的,主要提供服务注册与发现、动态负载均衡、可视化管理、定制化路由、安全反扒、Session ID复用、熔断降级、一键截流和性能统计等功能。
2. 基于Java语言的网关
Zuul/Zuul2
项目地址:https://github.com/Netflix/zuul
Zuul是Netflix开源的API网关系统,它的主要设计目标是动态路由、监控、弹性和安全。
Zuul的内部原理可以简单看作很多不同功能filter的集合(作为对比,ESB也可以简单被看作管道和过滤器的集合)。这些过滤器(filter)可以使用Groovy或其他基于JVM的脚本编写(当然Java也可以编写),放置在指定的位置,然后可以被Zuul Server轮询,发现变动后动态加载并实时生效。Zuul目前有1.x和2.x两个版本,这两个版本的差别很大。
Zuul 1.x基于同步I/O,也是Spring Cloud全家桶的一部分,可以方便地配合Spring Boot/SpringCloud配置和使用。
在Zuul 1.x里,Filter的种类和处理流程如图7-7所示,最主要的就是pre、routing、post这三种过滤器,分别作用于调用业务服务API之前的请求处理、直接响应、调用业务服务API之后的响应处理。
Zuul 2.x最大的改进就是基于Netty Server实现了异步I/O来接入请求,同时基于Netty Client实现了到后端业务服务API的请求。这样就可以实现更高的性能、更低的延迟。此外也调整了Filter类型,将原来的三个核心Filter显式命名为Inbound Filter、Endpoint Filter和Outbound Filter,如图7-8所示。
Zuul 2.x的核心功能:服务发现、负载均衡、连接池、状态分类、重试、请求凭证、HTTP/2、TLS、代理协议、GZip、WebSocket。
SpringCloud Gateway
项目地址:https://github.com/spring-cloud/spring-cloud-gateway/
Spring Cloud Gateway基于Java 8、Spring 5.0、Spring Boot 2.0、Project Reactor,发展得比Zuul 2要早,目前也是Spring Cloud全家桶的一部分。
Spring Cloud Gateway可以看作一个Zuul 1.x的升级版和代替品,比Zuul 2更早地使用Netty实现异步I/O,从而实现了一个简单、比Zuul 1.x更高效的、与Spring Cloud紧密配合的API网关。
Spring Cloud Gateway里明确地区分了Router和Filter,内置了非常多的开箱即用功能,并且都可以通过Spring Boot配置或手工编码链式调用来使用。
比如内置了10种Router,直接配置就可以随心所欲地根据Header、Path、Host或Query来做路由。
核心特性:
-
通过请求参数匹配路由;
-
通过断言和过滤器实现路由;
-
与Hystrix熔断集成;
-
与Spring Cloud DiscoveryClient集成;
-
非常方便地实现断言和过滤器;
-
请求限流;
-
路径重写。
graviteeGateway
项目地址:https://gravitee.io/与https://github.com/gravitee-io/gravitee-gateway
KaazingWebSocket Gateway
项目地址:
https://github.com/kaazing/gateway与https://kaazing.com/products/websocket-gateway/
Kaazing WebSocket Gateway是一个专门针对和处理WebSocket的网关,宣称提供世界一流的企业级WebSocket服务能力。具体如下特性:
-
标准WebSocket支持,支持全双工的双向数据投递;
-
线性扩展,无状态架构意味着可以部署更多机器来扩展服务能力;
-
验证,鉴权,单点登录支持,跨域访问控制;
-
SSL/TLS加密支持;
-
WebSocket keepalive和TCP半开半关探测;
-
通过负载均衡和集群实现高可用;
-
Docker支持;
-
JMS/AMQP等支持;
-
IP白名单;
-
自动重连和消息可靠接受保证;
-
Fanout处理策略;
-
实时缓存等。