网关一词来源于计算机网络中的定义,网关(Gateway)又称网间链接器、协议转换器。网关的准肯定义是: 两个计算机程序或系统之间的链接,网关做为两个程序之间的门户,容许它们经过不一样计算机之间的协议通讯来共享信息。顾名思义API网关就是API之间相互调用的关卡和屏障。html
试想一下咱们在实现一个很是庞大的业务系统,分为不一样的业务domain和子系统,各个domain和子系统提供处理业务的API,不一样系统之间以API的方式进行数据交互。一般状况下咱们可能会将全部实现业务功能的API集成到一块儿(API Center)给不一样的Channel的Portal提供数据处理的能力。当有一天咱们的系统须要与第三方发生交互,咱们既须要暴露给外部系统调用的公开API,同时也须要调用外部的API实现自身的业务需求。此时咱们将会考虑不少的问题,好比:服务之间访问的受权和认证,安全和性能的监控,缓存和日志的处理,超时的Retry,负载和熔断的处理,查询请求的聚合等等一系列的问题。此时你须要一个能够集中处理全部可能在服务调用之间须要处理的一切事情,就像是小区的物业和安保同样,须要对小区全部的业主处理职责范围内的一切事情。web
这是一般状况下API网关须要帮咱们处理的事情,随着系统业务的不断复杂化,咱们的系统越越庞大,API的交互愈来愈错综复杂。此时咱们可能会考虑将这个庞大的系统拆分红多个细小的domain,分别提供各自domain的API。这即是时下最流行的话题:微服务。当咱们的系统演进到微服务的架构时,API网关将是系统必不可少的关键部分。在微服务体系结构中,客户端应用程序一般须要使用多个微服务的功能。客户端若是直接消费某服务,那一般状况下将须要处理和协调用多个微服务endpoint。当应用程序引入新的微服务或更新现有微服务时会发生什么?试想一下若是你的应用程序有许多微服务,那么处理和协调来自客户端如此多的endpoint的请求,那对系统来讲是一场噩梦,并且因为客户端应用程序将与这些endpoint产生耦合,这将会使咱们的系统边的混乱不堪。编程
所以,咱们须要一个中间层或间接层(Gateway)来处理不一样client对API的请求,这将会使得咱们的应用程序处理起来很是方便。若是没有API网关,客户端应用程序必须直接向微服务发送请求,这就会产生不少混乱的问题,好比:c#
耦合: 若是没有API网关,客户端的应用程序将与内部微服务间耦合。客户端序须要知道实现业务需求的API分散在服务中的哪些部分,当咱们开发和重构内部服务时,将会影响到客户端应用程序,而且很难维护,由于客户端应用程序须要跟踪多个服务的endpoint后端
屡次请求:客户端应用程序中的一个页面可能须要屡次调用多个服务来完成某个功能,这可能致使客户端和服务器之间的屡次往返请求,增长了显著的延迟。咱们知道在中间级别处理的聚合能够提升客户端应用程序的性能和用户体验。设计模式
安全问题:若是没有网关,全部的服务都必须公开给“外部世界”,这使得攻击面比隐藏内部服务更大,而这些服务不是客户端应用程序直接使用的。攻击面越小应用程序就越安全。api
横切关注点:每一个公开发布的服务都必须处理诸如受权、SSL等问题。在许多状况下这些关注点能够在一个层中处理,这样内部服务就能够简化,这让我想起了面向切面的编程(AOP)浏览器
当咱们在使用多个客户端应用程序设计和构建大型或复杂的基于微服务的应用程序时,能够考虑使用API网关,这是为某些微服务组提供单一入口点的服务,它相似于面向对象设计的Facade(外观类)模式,但在微服务中它是系统的一部分。API网关模式的一个变体也称为“Backend for front-end”(BFF),由于你可能会根据每一个客户端应用程序的不一样需求建立多个API网关。所以API网关位于客户端应用程序和微服务之间,它充当反向代理将请求从客户端路由到服务,它还能够提供额外的横切特性,如身份验证、SSL终止和缓存。缓存
下面的图显示了自定义API网关如何适合于基于微服务的体系结构。安全
在上面的示例中,API网关将做为自定义Web API或ASP.NET WebHost服务的一个容器运行
在该图中须要强调的是咱们将使用一个面向多个不一样客户端的自定义API网关服务。这多是一个重要的风险,由于你的API网关服务将根据客户端需求的不断增加和发展,最终因为这些不一样的需求,它将变得臃肿不堪,实际上它可能很是相似于单片应用程序或单片服务。这就是为何咱们很是推荐将API网关拆分为多个服务或多个更小的API网关。
在使用API网关模式时咱们也要很是当心,一般使用单个API网关聚合应用程序的全部内部微服务不是一个好的实践,由于一旦这样作了它就充当一个总体聚合器或协调器并经过耦合全部微服务来违反微服务自治。所以API网关应该基于业务边界和客户端应用程序进行隔离,而不是做为全部内部微服务的单一聚合器。当把API网关层分解为多个API网关时, 若是你的应用程序有多个客户端, 这能够是一个主要的枢纽来识别多个API的网关类型,这样你就能够有不一样的外观类来应对每一个客户端的需求。这是咱们称之为“Backend for front-end”的模式(BFF),其中每一个API网关能够为每一个客户端提供不一样的API,甚至可能基于客户端的特定需求实现特定的适配器代码,该代码在下面调用多个内部微服务,以下图所示:
上图展现了一个带有多个细粒度API网关的简化体系结构,在这种状况下识别每一个API GateWay的边界纯粹是基于BFF的模式,所以只是基于每一个客户端提供各自所需的API,但在较大的应用程序也应该更进一步,以建立基于业务边界的网关做为第二设计衡量因素。
API网关能够根据产品的不一样提供多种特性,它可能提供更丰富或更简单的特性,可是对于任何API网关来讲,最重要和基本的特性是如下设计方式:
反向代理或网关路由:API网关提供反向代理,将请求(一般是Http请求)从新定向或路由到内部微服务的端点。网关为客户端应用程序提供一个endpoint或URL,而后在内部将请求映射到一组内部微服务。这个路由特性有助于从微服务的方式来解耦客户端,并且也很方便在单一API和客户端之间实现网关的控制,这样的话你能够添加新的API做为新的microservices同时仍然使用遗留单一的API,直到它在将来被分红许多microservices。由于API的网关的存在,客户端应用程序不会注意到所使用的API实现为内部microservices或单一的API,当在演进和和重构咱们的单一API到 microservices的过程当中由于有了API网关路由的存在,才不会带来Client请求的URI的变化。想了解更多网关路由的东西请戳这里。
请求聚合:做为网关模式的一部分,你能够将针对多个内部微服务的多个客户端请求(一般是Http请求)聚合到单个客户端请求中。当客户端页面须要调用来自多个微服务的数据时,这种模式特别方便。使用这种方法客户端将发送一个请求到API网关,而后网关将负责发送多个请求来获取内部microservices而后聚合结果再发送回客户端。这种设计模式的主要优势和目标是减小客户端应用程序和后端API之间的隔阂,对于微服务所在的数据中心以外的远程应用程序来讲这一点尤其重要,好比移动应用程序或来自客户端远程浏览器中的Javascript的SPA应用程序的请求。对于在服务器环境中执行请求的常规web应用程序(如ASP),这种模式并不重要,由于延迟比远程客户机应用程序要小得多。是否可以执行此聚合取决于你使用的API网关产品,然而在许多状况下,在API网关的范围内建立聚合微服务将会更加的灵活,因此你也能够在代码中定义聚合(即c#代码)。想了解更多请求聚合的东西请戳这里。
横切关注点或网关卸载:根据每一个API网关产品提供的特性,你能够将功能从单个微服务转移到网关,经过将横切关注点合并到一层来简化每一个微服务的实现。这对于能够在每一个内部微服务(如如下功能)中正确实现的复杂的特殊功能来讲特别方便。
身份验证和受权
服务发现集成
响应缓存
重试策略,断路器和QoS。
速度限制和节流
负载平衡
日志记录、跟踪、相关性
头文件、查询字符串和声明转换
IP白名单
根据每一个实现API网关产品能够提供更多的横切关注点,但这些都是最多见的特性。例如Azure API管理提供了这些特性中的大部分,以及许多对商业API很是有用的高级特性。可是对于更简单的方法,像Ocelot这样的轻量级API网关是至关灵活的,由于你能够将它部署到你所选择的环境和你的微服务。有关网关卸载模式的更多信息请戳这里。
本篇文章主要是介绍了API的网关模式的特性,文章是来自微软官方博客并加入了本身的一点理解。译文来自:https://blogs.msdn.microsoft.com/cesardelatorre/2018/05/15/designing-and-implementing-api-gateways-with-ocelot-in-a-microservices-and-container-based-architecture/
参考资料:
API Gateway
http://microservices.io/patterns/apigateway.html
https://docs.microsoft.com/en-us/azure/architecture/microservices/gateway
Aggregation and composition pattern