编辑推荐: |
本文以运营商BSS账务中心系统的云原生微服务架构演进实例,分享云原生架构落地过程遇到的困难及其成果
。
本文来自于公众号:
浩鲸科技
,由火龙果软件Alice编辑、推荐。 |
|
导读:
伴随云计算的滚滚浪潮,云原生(CloudNative)的概念应运而生。近年来,在企业数字化转型进程不断提速背景下,云原生技术飞速发展,已在众多行业和领域都有了许多成功落地案例,以kubernetes、微服务、服务网格、serverless、DevOps为代表的云原生技术已走向成熟和广泛应用,顺势而为全面拥抱 即将到来的 云原生时代。
01 古老的tuxedo之殇
十几年前,weblogic+tuxedo是运营商账务中心的标准技术架构,tuxedo服务框架作为核心的服务框架,承载着账务中心的核心服务功能,技术架构如下:
随着运营商业务不断发展,特别是经历了4G互联网时代的高速发展,到现在5G物联网时代的开启,老旧的tuxedo服务架构早已难以满足业务发展的要求,主要存在如下弊端:
- 有状态,不支持容器化部署,部署繁琐易出错 :只能采用传统人工或脚本的升级部署方式,升级过程需要停系统,只能一台主机一台主机的升级,升级过程繁琐耗时,容易出错。
- 无法水平扩展,可靠性差,系统扩容困难 :增加主机需要人工部署应用,修改配置,并将整个系统全部重启。
- 系统耦合高,可扩展性差 :新增交易需要重新编译,修改相关前后端配置文件,重新部署应用,需全量重启tuxedo和weblogic服务。
- 缺少服务自治能力,可维护性差 :系统难以维护,出现队列积压,进程异常退出、主机故障等问题,缺乏告警机制,且问题定位和排查难度大,故障恢复时间长。
- Tuxedo和weblogic均为海外商用软件,在国内核心技术要自主的大背景下,去IOE及海外商用软件已上升到政治高度。
02 微服务架构演进之路
2012年以后,随着移动互联网的兴起,微服务思想就应运而生。2015年左右国内大厂开始进行项目升级,转战微服务,2017年传统企业也纷纷踏上了微服务架构升级之路。在这一年,我们也开始了账务中心微服务化演进之路,准备一次性彻底解决掉tuxedo这个历史包袱,但迎接我们的并非一番风顺。
帐务中心dubbo化改造之苦
当时Dubbo & Spring Cloud两大主流的开源微服务框架。鉴于Dubbo相对Spring Cloud框架的简单和轻量型以及在性能上的优势,我们选择了Dubbo框架,然后兴致勃勃的开始了服务Dubbo化之路。
账务中心服务dubbo化技术架构图如下:
经过长达一年半的服务dubbo化改造之后,我们不得不承认当初选择了一条耗费人力的痛苦之路:
跨语言改造之苦:
Dubbo & Spring Cloud都属于JAVA技术栈,对于完全使用C++开发的tuxedo服务,跨语言是我们面临的第一道坎。我们痛苦的选择将tuxedo服务使用JAVA语言重写,但最终工作量及重写风险,让我们止步于查询功能重写,而大部分核心功能仍然无法摆脱Tuxedo,只能通过RocketMQ来尽量将同步调用改为异步调用的C++消费者。
服务治理之苦:
Dubbo服务的治理能力非常弱,面对客户对于安全认证、服务限流、服务熔断、灰度发布、服务在线发布等能力的需求,开源的Dubbo服务框架均不支持,于是我们只能通过对Dubbo服务调用的泛化接口增强封装或通过Dubbo过滤器扩展一些安全认证、灰度发布、服务限流等完善性功能
性能调优之苦:
由于服务可观测性较弱,缺少服务调用链,在性能压测时只能通过原始的不断增加性能相关日志的方式,性能问题定位和调优工作效率极低,类似线程池大小及数据库连接池参数不合理导致的获取连接超时,以及SQL并发执行的超时等异常超时情况,在上线后经过了2个月的痛苦周期才将dubbo服务性能渐渐调优稳定。
传统微服务框架Dubbo & Spring Cloud的局限
跨语言问题:均属于JAVA技术栈,不支持其他语言的RPC调用。对于使用其他语言(如C++)开发的应用改造为微服务架构无法使用,只能考虑重写。 应用耦合高:基于注册中心实现服务动态发现,各自有自己的应用技术框架,业务应用与框架深度绑定,强耦合。应用需要进行框架改造,并且需要配套相关组件及配置。 服务治理能力弱:dubbo服务治理能力最弱,本质上只能算一个分布式RPC框架,只有基础的服务发现,限流、熔断、灰度发布、智能路由、追踪等微服务框架能力均需要自行定制完善。 缺少部署与运维能力:spring cloud的服务治理能力需要通过集成各种配套组件实现,并且也缺少灰度发布、服务调度、故障自愈、弹性伸缩这些运维能力。
新一代微服务架构Istio & Grpc
随着容器化技术的普及,kubernetes生态的不断完善,基于kubernetes的微服务架构也应运而生。在经历了账务中心服务dubbo化的痛苦之后,我们也终于找到了新的出路,即基于k8s的Istio & Grpc。
服务网格Service Mesh的设计理念
首先,吸引我们的是服务网格的设计理念,Service Mesh是在网络层TCP/IP上建立的一个中间层,接管服务之间的通信流量,将微服务治理能力下沉,从而实现对上层 应用透明、不限制语言、无侵入 的享受微服务能力。这不正好解决了我们经历的服务Dubbo化的痛点问题吗?
通过在应用服务旁边注入一个SideCar代理,实现对服务网络流量的拦截。将服务之间的通讯完全交给由SideCar代理组成的服务通信网络,将微服务等能力均下沉到Sidecar代理中实现,从而对应用透明无侵入。
服务网格Istio架构
由于kubernetes与Istio的天源互补,Isito是CNCF云原生基金会首推的云原生微服务架构,经过几年的发展,Istio已成为服务网格众多实现方案中当之无愧的最佳开源实践,成为大家在服务网格技术选型时的默认选项。
Istio主要功能特性:
量管理:为HTTP、gRPC、TCP等流量路由和控制,最新版本已支持Dubbo协议。
动态路由:通过丰富的路由规则、重试、故障转移和故障注入对流量行为进行细粒度控制。
控制策略:可插拔的策略层和配置API,支持访问控制、速率限制和配额。
可观察性:服务间流量的自动化度量、日志记录和追踪。
安全:基于身份验证和授权的,实现安全的服务间通信。
Kubernetes+istio的主要优势:
应用无侵入:服务网格独立部署配置,对应用程序透明无感知、程序语言无关、RPC框架无关,应用改造量极小即可实现微服务架构。
Istio与k8s天然融合:服务治理、观测及运维平台相关能力完备,开箱即用。Dubbo框架服务治理能力弱,Spring Cloud虽通过各种组件补齐服务治理能力,在没有k8s的加持下,它们都缺少部署与运维的能力,因此都需要使用dubbo/Spring Cloud与k8s的融合方案。Istio也就成为Dubbo、Spring Cloud与k8s融合的桥梁。
03 账务中心微服务化实践
跨语言解决方案
gRpc是开源的轻量级跨语言的RPC框架,gRpc是Istio的头号公民。
1.使用Grpc实现跨语言的RPC调用,通过搭建底层C++的grpc Server公共框架替代tuxedo服务,在tuxedo服务入口做grpc服务适配改造,复用现有的C++业务核心代码,从而将应用的改造工作量控制到最小。
2.引入Istio服务网格(service mesh),构建服务通信网络中间层,由k8s+istio来实现微服务的服务发现、负载均衡、服务路由、熔断限流、鉴权、灰度发布等微服务能力。
基于业务指标的动态伸缩
K8s中几种典型的动态伸缩机制:
1) 基于HPA的弹性伸缩 K8s 原生的 HPA支持基于CPU、Memory的自动扩缩容。 利用Prometheus adapter可获取prometheus自定义指标扩展。 通过CronHPA扩展定时自动扩缩容。
2) 基于KPA的弹性伸缩 Knative Serving 自动扩缩容(KPA):基于服务并发请求指标的秒级扩缩容(仅支持HTTP/GRPC),支持缩容至0和从0到1的冷启动 Knative eventing 自动扩缩容(KPA):基于服务并发请求指标的秒级扩缩容,支持0-1的冷启动。
账务中心的弹性伸缩应用场景: 1) 账务HTTP&GRPC服务采用KPA,knative的动态伸缩优点是对于突发流量能够做到秒级伸缩。HPA伸缩是分钟级,5分钟的稳定期,且prometheus的扩展业务指标采集本身存在30s以上延迟。 2) 银行接口、DCC接口、Dubbo服务只能使用HPA+prometheus自定义指标方式,而istio默认内置了jaeger+prometheus+grafana等服务监控与日志追踪的开源组件,并默认进行了jaeger埋点、生成了prometheus的服务性能及交易量等服务指标,直接可用于hpa中,无需应用再做任何埋点和指标采集的适配改造。 3) 定时任务、日月账任务、批量任务适合采用定时伸缩,如下账的任务可以在下账前扩展执行器和批量处理服务数量。
全系统、微服务粒度的灰度发布
基于Nginx的灰度发布,局限在接入层进行灰度路由,AB部署模式浪费资源,灰度粒度大,并且基于内容的灰度发布依赖定制的lua插件实现。
常见web或者http接口的灰度发布实现,主要通过前端Nginx反向代理中注入lua插件实现灰度路由,不能单独针对后端服务(dubbo服务、grpc服务)的灰度发布,因此通过采用AB两套部署模式,灰度发布粒度大;另外,由于各类应用接口协议、web端参差异大,自定义lua插件通用性较差。
Dubbo和spring cloud均有各自的灰度发布,应用场景局限在各自的服务框架中,通用性差,各自配置和实现方式差异大。
spring cloud依赖zuul或cloudgateway网关实现灰度路由策略,对于Dubbo服务通常是在服务消费端实现自定义的灰度路由规则。将Dubbo灰度发布、spring cloud灰度发布以及Nginx灰度发布结合起来,可以实现服务粒度的灰度发布。但由于它们各自的实现方式各不相同,往往还需要统一定义一个统一灰度发布规则配置和操作界面来屏蔽配置和操作上差异,降低配置和操作复杂度,增强易用性。
Isio则通过其动态路由能力实现 全系统、服务粒度、统一方式、灵活灰度策略 的灰度发布。应用无侵入,无需额外的开发,配置也采用k8s的yaml文件定义,配套helm可实现一键灰度发布,一键滚动更新。
营业WEB:采用cookie中的工号作为灰度规则进行路由; 集团OpenAPI:采用http header中的渠道ID和应用ID作为灰度规则进行路由; WS接口:采用流量权重的灰度发布;银行接口和DCC接口服务已稳定无需灰度发布; Dubbo&Grpc服务:采用Grpc Header或者Dubbo context中的工号、账户ID、测试号码作为灰度规则进行路由; 异步实时任务:MQ消费者进程内部调用Grpc或者Dubbo服务,也通过Istio实现按照工号、账户ID、测试号码作为灰度规则路由。
零信任网络的服务安全
双向TLS身份验证:服务之间通过sidecar之间双向 TLS 握手,验证服务器证书中提供的服务帐户是否有权运行目标服务,无需更改应用程序代码和基础架构,通过简单配置实现默认的服务安全。
JWT+HTTPS的接入身份认证:利用Istio基于JWT的身份认证机制,在IngressGateWay入口网关进行JWT有效性的验证。实现外部CRM统一门户接入WEB的身份认证。
通过CRM统一门户登录认证服务生成JWT签名,在访问账务web界面时在header中携带JWT。 Authorization: Bearer <jwt token> 利用Istio基于JWT的身份认证机制,在IngressGateWay入口网关进行JWT有效性的验证,通过验证方可访问账务web。 统一门户与ingressgateway,ingressgateway与账务web服务之间均采用tls协议加密传输,防止JWT泄露。
04 结语
云原生的微服务架构k8s+istio+grpc,凭借其应用无侵入、语言无关、框架无关(兼容dubbo)、服务治理能力完备、开箱即用、与k8s天然融合互补等独特优势,提供了一个普适度广、应用改造成本小、风险最低、服务治理功能完备,并充分利用了k8s原生部署和运维能力的解决方案。我们的账务中心微服务化之路最终也通过该解决方案,最终从dubbo化改造的泥潭中得以解脱,也让我们成为云原生技术的热衷追随者,顺势而为全面拥抱云原生时代吧!
|