Gloo+Dex+OPA 还是 APISIX+Dex+Casbin?

时间:2022-12-07 15:05:39

背景介绍

Zadig 是基于 Kubernetes 打造的开源、企业级一体化云原生 DevOps 平台。它具备灵活易用的高并发工作流、面向开发者的云原生环境、高效协同的测试管理、强大免运维的模板库、客观精确的效能洞察以及发布编排工作流、客户中心等重要特性,为工程师提供统一的协作平面。

Zadig 网关层主要引入 Gloo Edge、认证和授权组件 OPA、身份认证组件 Dex,最终支持了业务所需的灵活的 RBAC、ABAC 权限管理、统一用户支持接入 LDAP(AD、OpenLDAP)、OAuth 2.0、GitHub 等能力,但不同应用场景有不同的诉求,本文仅将 Zadig 场景下的架构选型思考分享给社区供参考。

Zadig 使用 API Gateway 的必要性

面向企业级的研发场景,需要提供更为强大的系统级管理能力。同时 Zadig 的服务数量也在增加,企业级能力要求越来越高,势必对服务调用提出更高的要求:

  1. 1. 客户端维护负担需要降低,通过统一网关访问管理多个服务地址

  2. 2. 面对业务变化,接口重构时调用方不须了解接口本身的拆分和聚合

  3. 3. 客户端无须关心接口协议,内部可以使用多种不同的协议(http,rpc,amqp)

  4. 4. 统一身份认证,权限控制,接口请求访问日志统计等

  5. 5. 隔离内外部 API,以提升系统的健壮性和安全性

  6. 6. 通过服务动态注册,负载均衡,流量复制、染色等机制,实现灰度发布,服务调试等功能

Zadig 的访问入口有 Portal 和 IDE 插件 Toolkit 两种,出于以上的考虑,初步对网关架构做以下设想:

Gloo+Dex+OPA 还是 APISIX+Dex+Casbin?

有哪些需求需要被实现?

除了满足当下的业务需要,同时需要考虑到未来的可扩展性和应用场景,对短期和中长期需求做了如下梳理,以确定我们后续的技术方向。

短期需求

  • • 反向代理:这个是核心需求,需要为所有访问后端 API 提供一个单一入口,同时隔离内外部的 API

  • • 认证:这个也是刚需场景,Zadig 是面向大型团队的工程师群体提供服务,认证中心需要提供多种认证方式以供统一登录,比如支持用户名密码,LDAP/AD,第三方 SSO,OAuth2,GitHub/GitLab/Google/... 等

  • • 授权:Zadig 面向开发者的资源主要是工作流和集成环境,需要满足不同项目下开发、测试、运维场景下的业务分离。所以需要通过可配置的策略提供多样化的权限控制。

  • • 缓存:如果能缓存频繁请求的数据,可以减少网络带宽和往返时间的消耗,提高性能,尤其是对于 GitHub 这种访问比较困难的资源

  • • API 聚合:面向特定的业务场景需要聚合某些 API 请求,减少请求数量,降低前后端的耦合,以提升开发和协作效率

  • • 请求 / 响应重写:支持请求 url,header,body 的修改和响应状态,header,body 的修改

  • • 操作 / 请求日志:系统需要审计日志功能,来记录所有对系统的更改,所有请求的参数,响应时间等

  • • 负载均衡:通过一个传入的 URL 路由到多个后端目的地,扩展应用程序以实现高可用性

  • • 支持 WebSocket:许多动态和实时功能可以通过 WebSockets 来解决,以减少频繁数据传输的多个 HTTP 调用的开销

  • • 支持 gRPC:gRPC 通过利用 HTTP/2 进一步降低负载,可以有效地用于服务之间的相互通信

 

中长期需求

  • • 子环境:暂时还不是刚需,但随着微服务的不断迭代,完整拉起一套系统会资源开销增大。子环境可以只部署需要开发或者调试的部分服务,其他服务可以直接使用父环境

  • • IP 列表:当未来提供公有服务时,为系统提供额外的安全层,当发现一组恶意地址试图通过使用 DDoS 类攻击时使应用程序免于瘫痪,允许或阻止某些 IP 地址通过。

  • • 速率限制:能够对 API 调用进行流控,例如只想允许所有使用者每分钟调用 10000 次,或者允许让某一特定使用者每月调用 1000 次

  • • 版本化:同时使用不同版本的 API ,或者提供金丝雀版本或蓝 / 绿部署、灰度发布能力

  • • 熔断器:提供在线服务时可避免服务中断,提供高可用的基础保障能力

选型调研

通过对需求的分析,我们找了一些资料做相应的对比选型,主要研究了 Zuul、Kong、APISIX、Tyk、Gloo、Emissary-Ingress 及 KrakenD,以下是对他们各自能力的简要分析:

Zuul

Zuul 是 Netflix 开源的微服务网关,Spring Cloud Netflix 全家桶之一。核心是一系列的过滤器,可以完成以下功能:身份认证与安全,审查与监控,动态路由,压力测试,负载分配等。

Kong

Kong 是一款基于 OpenResty(Nginx + Lua 模块)编写的高可用、易扩展的,由 Mashape 公司开源的 API Gateway 项目。Kong 通过插件(插件使用 Lua 编写)的形式提供负载均衡,日志记录,身份验证,速率限制,转换等功能。可以很轻松扩展功能,模块化,可以运行在任何基础设施上。

APISIX

APISIX 是一个基于 OpenResty 和 etcd 实现的云原生、高性能、可扩展的微服务 API 网关。APISIX 通过插件机制,提供动态负载平衡、身份验证、限流限速、配置和插件热更新等功能,并且支持你自己开发的插件(插件使用 Go/Python/Java 编写)。

Tyk

Tyk 是一款基于 Golang 和 Redis 构建的开源 API 网关,拥有丰富的功能集和漂亮的 Web-UI 仪表板,但是对商业用途不是很友好。

Gloo

Gloo 是一个基于 Envoy 的 Kubernetes 原生入口控制器和下一代 API 网关。Gloo 在函数级路由方面表现卓越,它支持传统应用程序、微服务与 Serverless(Gloo 被选为 Knative 项目的首选 ingress 项目)。Gloo 设计独特,可支持混合应用,其中的多种技术、架构、协议和云可以共存。

Emissary-Ingress (fka Ambassador API Gateway)

Emissary-Ingress 与 Gloo 类似,也是一个基于 Envoy 的 API 网关。

KrakenD

KrakenD 是一款基于 Golang 的高性能的开源 API 网关。它的核心功能是创建一个 API,该 API 充当许多微服务到单个端点的聚合器,为用户自动完成聚合,转换,过滤,解码,限制,身份验证等工作。

这些组件都有不同的应用场景和成熟度,我们得到一些初步的结论:

  1. 1. Zuul 适用于 Spring Cloud 生态

  2. 2. Kong 和 APISIX 特点类似,相比之下 APISIX 略胜一筹

  3. 3. Tyk 是纯 Golang 写的 API 网关,但是文档和用例比较少,对商业用途也不是很友好

  4. 4. Gloo 和 Emissary-Ingress 都是基于 Envoy 的 API 网关,相比 Gloo 资料更丰富一些

  5. 5. KrakenD 是另一个 Golang 写的 API 网关,API 聚合功能强大,但是比较小众

以上 API 网关都没有提供认证和鉴权或者功能支持的比较简单。认证基于 Dex 鉴权有两种方案:一种是基于 OPA 的 Envoy ,另一种是基于 RBAC 的 Casbin。APISIX 对 Casbin 的支持非常好。所以最终敲定了两套备选方案为 Gloo+Dex+OPA 或者 APISIX+Dex+Casbin

同时我们考虑到 Gloo 是 Kubernetes Native 的方案,基于 CRD 实现,完全依赖于 API Server,无状态。同时支持微服务,Serverless 和传统服务,未来可以无缝对接 Serverless 和 Service mesh,支持本地服务的特性也为本地调试带来可行性。所以最终选定为 Gloo 方案。

通过引入网关组件,最终 Zadig 系统架构呈现如下。

Gloo+Dex+OPA 还是 APISIX+Dex+Casbin?

关于 OPA、Dex 的详细技术实现:

 

参考链接

• https://www.bbva.com/en/api-gateways-kong-vs-tyk

• https://www.krakend.io/docs/overview/

• https://github.com/apache/apisix

• https://github.com/Netflix/zuul

• https://github.com/Kong/kong

• https://github.com/TykTechnologies/tyk

• https://zhuanlan.zhihu.com/p/103236688

• https://mahesh-mahadevan.medium.com/my-experiences-with-api-gateways-8a93ad17c4c4

 

Zadig