武林外传—一灯大师与众弟子漫谈Api网关选型

2018-10-25 11:35:06 浏览数 (1)

南帝段王爷隐居桃源后,潜心研究,构筑了一套武林秘籍访问系统,系统是微服务部署的,拆分为多个模块,每个模块只做一件事情。系统刚上线的时候非常顺利,但随着访问量的增大,模块的增多,新问题越来越显现出来,他心中已有了七八成的主意,但想考一考身边渔樵耕读四大弟子,便将他们叫到自己跟前来,道:“自从我带你们隐居桃源,你们整日游山玩水,过得可是神仙般的日子,不知有没有忘记技术的学习呀?”

渔樵耕读四人齐声道:“不敢忘记师父的教导!”

“好,你们思考下这个问题。当前,我们的服务越来越多,导致客户端调用服务api时非常地麻烦,比如,有人要看一阳指秘籍,客户端首先要访问身份认证服务,然后是书籍查询服务,然后是模拟演练系统,它需要知道怎么去消费这三个不同的服务,而我们管理这些对外开放的接口也是一个问题。还有一个更要命的,最近欧阳锋对九阴真经可谓虎视眈眈,我们的鉴权代码散落在各个服务中,这样的话工作量加大了,维护也非常不便,若是一个服务的鉴权代码出了问题,欧阳锋之辈便可以乘虚而入了。”

书生朱子柳是四弟子中最有学问的一个,他一听便已明了,道:“师父,我们可以搭建一个网关系统,让所有的外部请求都访问这个Api网关,由网关来完成请求路由、权限验证、负载均衡等功能。”

一灯大师捻须微笑道:“说得在理,不过笼统了些,Api网关,用什么网关呢?”

樵夫道:“这选择实在是多,有nginx,zuul,最近又推出了Spring cloud Gateway和zuul2。”

一灯大师道:“那你能说说他们之间的区别吗?”

“这,这,嘿嘿......”樵夫摸摸脑袋笑着。

渔夫接过话来:“nginx以前主要是用作反向代理,如果要做一个完整的网关功能需要结合Lua进行扩展,Nginx 采用了异步非阻塞的方式来处理请求,可以同时处理成千上万个请求的。一个 Worker 进程可以同时处理的请求数只受限于内存大小。目前市面上有基于nginx lua的框架,如Kong / Openresty,它借助于Nginx的事件驱动模型和非阻塞IO,性能方面是非常棒的,下面是一个测试报告,在单核和双核测试环境下,除直接访问外,nginx的性能是最好的。”

命令模版:

代码语言:javascript复制
ab -n 10000 -c 200 HTTP://<server-address>/<path to resource>

详细测试报告: https://engineering.opsgenie.com/comparing-api-gateway-performances-nginx-vs-zuul-vs-spring-cloud-gateway-vs-linkerd-b2cc59c65369

“那zull呢,还有更新一些的Spring cloud Gateway和zuul2。zull是Netflix 开源的微服务网关组件,和spring cloud那一套结合得还是挺好的,我们的系统正是基于spring那一套搭建的,而且zull提供了许多的核心过滤器,通过这些过滤器,我们可以做许多的事,像动态路由、负载均衡、压力测试等等,这些Nginx提供的并不全……全面。而且,我们也看到图了,在较强的测试环境下(8 核),直接访问、Nginx、Zuul 差距不大。” 农夫武三通说的太快,显得有些结巴了。

朱子柳道:“你们难道对这个测试结果没有任何怀疑吗?我们的架构虽然用了spring boot的,但主要还是架构于Dubbo之上的,况且zull基于 Servlet 框架构建,采用的是阻塞和多线程方式,即一个线程处理一次连接请求,当出现问题时,如后端延迟或设备错误重试,活跃的连接和线程数量会增加,这会加大服务器负载并可能使集群无法承受。较新的Spring cloud Gateway和zuul2倒是不错,zull2基于Netty,是非阻塞的,支持长连接,但Spring Cloud暂时还没有整合计划,这个高性能版的Zuul 2在经过了多次跳票之后,Spring可能不愿意再继续等待,便自己研发了Spring Cloud Gateway,这才是真正和spring cloud高度整合的,刚出来不久,有人对它的性能作过测试,从上面图表看,性能并不理想,但测试结果并不准确,对此官方已经作了说明(https://github.com/spring-cloud/spring-cloud-gateway/issues/124) ,主要是说Spring Cloud Gateway依赖Reactor Netty,Reactor Netty不支持HTTP 1.0,用ab作压测结果并不准确,使用wrk测试结果如下,Avg Req/Sec/Thread值是zuul的近1.6倍。”

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

“那你是支持用Spring cloud Gateway的喽?”渔夫问道,他一向很重视这位读书人的意见。

“网关的选型,没有最好的,就看适合不适合现有系统的,目前,弟子几个功力有限,不然完全可以基于Netty自主研发一个网关系统。目前从性能上讲,这些技术都是足够应付目前的访问量的,从与现有系统的整合来看,我们内部服务是使用Dubbo和zookeeper实现服务间的注册与发现的,当在Dubbo中使用基于HTTP的REST协议,后端服务才能被zuul直接调用,假如采用服务发现的形式调用服务,zuul可以通过Netflix/eureka实现服务发现,而Dubbo与eureka又不能很好地结合……”朱子柳陷入了沉思之中。

一灯大师见弟子说到了要紧处,道:“这点你考虑得非常好,不过,不用担心,其实很久以前,大理王宫里的系统就用过zuul,也遇到类似的问题,当时有位高人自己研发了一套内部接口,用于服务发现,只要对接这套接口,传入应用名称和环境,返回ip列表,就可以实现了。”

“关于整合方面,还待我深思,单考虑网关本身,我们该选择什么呢?”朱子柳问。

“刚才你们都列举了几个方案,Kong,zuul,zull2,Spring Cloud Gateway。哪一种方案你们最有把握实现。”

“我们都是java一系的,对Kong的扩展不够熟悉,而且对新出不久的技术不放心使用,从网上的性能测试争议也可知新技术使用还未经历足够的实践的考验。既然大理段氏对zuul有过丰富的使用和扩展经验,而且依据现有的每秒请求量,也足够应付了,那就,那就用它吧?” 渔夫道。

一灯大师想:这些弟子,只想着用现成的成熟老技术,也不无不妥,目前系统急需改造,让弟子们深入了解这些框架,仔细考证,也不是一时之间的事情,自己已经放手让他们去干了,不便干涉,但以后必须对他们进行全方位的培养。

“你们知道怎么用zuul搭建一个网关吗?关于zuul的使用,你们先看下这幅图。请求的周期基本如此。主要是pre、route、post三种类型的过滤器。”

“嗯,这个实际配置也很简单呀,如果使用spring boot的话,只要在应用主类加@EnableZuulProxy开启zuul,再在application.properties中配置Zuul应用的基础信息,如:应用名、服务端口,路由等,如果需要自定义过滤器,实现ZuulFilter接口即可,官网上都有。”渔夫道。

官网配置步骤: https://spring.io/guides/gs/routing-and-filtering/

“很好,不过这只是冰山一角,你知道,加上@EnableZuulProxy,代表添加了多少默认的过滤器吗?”一灯大师道。

“这……” 渔夫和农夫面面相觑,又看看书生。

“这个我倒是曾有过些了解。” 书生朱子柳大笔一挥,在墙上画了张表格。

类型

顺序

过滤器

功能

pre

-3

ServletDetectionFilter

主要用来检测当前请求是通过Spring的DispatcherServlet处理运行,还是通过ZuulServlet来处理运行的

pre

-2

Servlet30WrapperFilter

主要为了将原始的HttpServletRequest包装成Servlet30RequestWrapper对象

pre

-1

FormBodyWrapperFilter

将符合要求的请求体包装成FormBodyRequestWrapper对象

pre

1

DebugFilter

标记调试标志,根据配置参数zuul.debug.request和请求中的debug参数来决定是否执行过滤器中的操作

pre

5

PreDecorationFilter

处理请求上下文供后续使用

route

10

RibbonRoutingFilter

serviceId请求转发

route

100

SimpleHostRoutingFilter

url请求转发

route

500

SendForwardFilter

forward请求转发

post

0

SendErrorFilter

处理有错误的请求响应

post

500

SendForwardFilter

处理forward

post

1000

SendResponseFilter

处理正常的请求响应

“嗯,很好,学习技术,不仅要知道怎么用,还要尽可能多地知道它的原理,这样有什么问题也能很快找到思路去解决,不然,只能像无头苍蝇一样,网上各种搜索,一个个去试,最后就算解决了问题,脑子里还是一头雾水,这不利于你们将来的发展。”

“谢师父教诲。”渔樵耕读齐声道。

“去吧,这个事就交给你们了,有问题相互之间要及时沟通。” 一灯大师挥了挥手,让众弟子出去忙了。最近,他师弟从天竺带来微服务七篇,他要闭关细细研习一番,等参透了,和众弟子讲解。

java达人

ID:drjava

(长按或扫码识别)

0 人点赞