前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >降本40%,数数科技大数据查询引擎云原生实践

降本40%,数数科技大数据查询引擎云原生实践

作者头像
腾讯云原生
发布2023-03-30 08:40:18
8120
发布2023-03-30 08:40:18
举报
文章被收录于专栏:腾讯云原生团队

陈云,数数科技资深云原生研发工程师,专注于云原生在大数据场景下的应用探索。负责数数科技TE(新一代数据分析引擎)的云原生方向架构建设、优化和迭代。

背景

ThinkingEngine (简称“TE”)新一代数据分析引擎,由数数科技研发,提供一站式的数据应用服务。让数据分析能够覆盖全品类分析场景,帮助游戏公司专注在游戏本身的业务上,更好地挖掘数据价值。

我们常常会收到客户的反馈:在业务高峰时容易出现分析查询慢和卡顿的情况。造成这种现象的原因是查询引擎在业务高峰时资源瓶颈,查询只能排队等待。用户也采取过增加资源的方式来缓解这一状况,但是由于架构的耦合性,很多程序部署相互依赖,扩展比较困难。这也会导致资源的利用率在业务低谷时非常低。

这种方式在一定程度上缓解了查询慢的问题,但是需要付出更多的人力和服务器成本。我们通过架构的演进实现按需弹性资源,增强架构的扩展性。在提高查询效率的同时平衡服务器成本。

设计思路

整体方案设计围绕Trino查询引擎资源瓶颈问题来展开,并且需要兼顾到服务器成本。让Trino的架构具备资源弹性能力,在业务高峰时动态弹性扩资源,在资源负载低时释放资源,做到动态按需按量使用资源。

现有的部署方式是同一个节点可能会部署多个程序。同节点和跨节点的程序与程序之间又相互有依赖关系,这对于架构的扩展非常难。想要实现查询引擎的弹性能力,在架构上就需要做一些调整。这里借鉴了一些微服务架构的设计方法。单一职责原则,服务化设计,程序独立运维部署。

将Trino从原有的架构体系中分离出来,独立部署,独立维护和扩展。原有的架构通过配置切换即可使用到新的查询引擎的能力。新老查询引擎可以并存,按照架构实际使用效果逐步将老的查询引擎缩减直至完全下线,使Trino的计算资源具备弹性能力。

常见的方案如下两种( 以腾讯云平台为例 ):

节点伸缩组

节点维度来控制和管理计算资源,仍旧采用虚拟机部署的方式,利用云厂商的弹性能力实现按需弹性资源。

弹性容器

采用容器化部署,利用 Kubernetes HPA 的弹性伸缩能力来满足需求。

在腾讯云上的容器服务有两种:

TKE 普通节点

  • 全场景适用,完全兼容开源 Kubernetes 集群标准能力
  • 同时支持超级节点、原生节点、注册节点及 CVM
  • 支持资源可视化及优化分析,轻松提升资源利用率

TKE Serverless模式

  • 适用于高稳定性、高安全性常驻业务及临时计算任务
  • 支持安全沙箱容器,业务容器强隔离,无互相干扰
  • 可秒级启动上万 Pod,并按实际时长计费

节点伸缩组的优势在于架构简单,部署和维护方便。可以和现有的架构风格很好的兼容和融合(都是采用虚拟机的部署方式)。不足之处在于弹性的维度比较单一,只支持CPU或内存的指标进行弹性伸缩,且弹性效率不足,大概需要3min30s左右才能弹性好资源。

弹性容器云服务的优势在于可以无缝对接自动化CI/CD工具,可以更加细粒度、以更丰富的方式对资源进行调度和控制。k8s的HPA也很方便的支持多种类型的监控数据作为弹性指标,而且弹性速度也很快,可以较好地满足计算资源弹性需求。

我们是ToB的业务,服务器权限归属于用户。我们通常只能够通过有限的权限和访问路径帮助排查问题和更新、维护业务系统的版本内容,其中部署架构的简洁性也是一个重要参考维度。TKE Serverless模式刚好比较符合我们的期望。

弹性能力的设计大体方向,是利用云厂商的Serverless容器服务作为基础设施,然后根据实际业务需求进行调整和设计。云原生的架构通常不是孤立的存在。把Trino从原有的架构体系中分离出来,使用云原生的方式重新设计,就必然需要把服务治理的内容给补全(服务网关、服务编排、监控、日志和配置等),这样查询引擎云原生化才能真正有效运行起来。

实现落地

总体方案包括CI/CD、容器编排、资源调度、服务治理和可观测性,以下为核心价值模块的展开介绍:

弹性容器资源

预期能通过自定义的监控数据作为弹性伸缩指标,在超过阈值时弹性资源副本,低于阈值时缩减资源数量。始终能确保资源是按需调度和分配的。

Kubernetes的HPA支持CPU和内存维度的监控数据作为弹性指标,但是对自定义弹性指标支持不太友好。而我们的实际场景需要根据一些特定的业务监控数据(例如 : 消息队列积压数、请求处理等待时间等)来触发扩缩。

为此,我们利用Kubernetes API Aggregator的特性,支持将第三方的服务注册到Kubernetes API。这样就实现了直接通过Kubernetes API访问到外部服务,外部服务作为数据源,就有了更好的灵活性和扩展性了。具体落地时我们使用prometheus作为监控数据源,prometheus-adapeter作为扩展服务注册到Kubernetes API。整体逻辑架构图如下:

我们使用了HPA和CronHPA相结合的方式来应对不同的场景。负载缓慢增长的场景使用HPA根据业务指标进行控制,而在瞬时高负载场景下使用CronHPA,根据业务繁忙与空闲规律,提前自动调度好资源。在业务高峰之前扩资源,在业务空闲时释放资源,CronHPA极大缩短了应用冷启动时间。

服务接入

Kubernetes抽象了一层网络供pod相互访问,外部无法访问。外部想要访问Kubernetes通常会采用NodePort、LoadBalancer和Ingress等方式。因为K8s Serverless云服务的特殊性,底层Kubernetes工作节点是封装屏蔽的,所以选择通过云服务LoadBalancer将所有的请求转发到ingress-nginx-controller,再通过 ingress配置具体的路由转发规则。

镜象仓库

镜像仓库的设计也是经历了三次改进,有很多问题无法提前预判,我们基本上是在实际的问题和场景中一步一步迭代演进的。私有镜像仓库设计的目的是确保国内和海外的客户,稳定且可靠的获取系统容器镜像。在维护和管理上能做到镜像统一分发和同步到多区域镜像仓库,对外提供统一的域名访问。

阶段一: 能提供基本的镜像分发能力

存在问题:

a) 海外获取镜像非常慢

阶段二: 国内和海外提供镜像分发能力,稳定运行了很长一段时间

也暴露了两个问题:

a) 国内访问DockerHub服务网络延时和不稳定,经常造成弹性容器无法顺利启动。

b) DockerHub 自身对镜像获取频次和速率有限制,超过阈值就会服务不响应。

阶段三: 国内和海外提供稳定的镜像分发能力

a) DNS就近解析,国内解析到国内的镜像仓库,海外解析海外的镜像仓库

b) 镜像优先推送到国内仓库,然后由国内镜像仓库同步到海外和DockerHub

c) DockerHub依然保留作为备份,在异常时迅速切换使用

镜像加速

TKE Serverless 弹性资源非常快,但是Pod要消耗很长时间才能处于 Running 状态。我们排查了每个耗时环节发现,绝大部分的时间花在了 Trino 镜像获取上(大概耗时了3min左右)。Trino 镜像大概1.8G左右,在网络带宽不足时可能会消耗更多的时间。从外部来看就会发现弹性应用一直处于等待状态。用户可能需要等待很久,新弹性的应用才会处于 ready 状态,查询体验才会提升。

腾讯云上的镜像缓存云服务,刚好可以很好的应对大镜像获取问题。下面是一个 Trino worker Pod 部分启动事件消息。可以看到镜像已经存在无需重新拉取。

在使用过程中还遇到另一个问题,镜像缓存服务需要手动在云控制台配置,特别是每次镜像版本更新时都需要客户在控制台手动重建一次,整个过程非常麻烦。我们的ToB业务,对客户采用的是私有化部署,这给我们升级维护管理造成了很多不便。腾讯云容器团队,在接收到我们的需求之后,迅速协调研发资源,推出imc镜像加速组件,采用imc组件来实现对镜像缓存的版本管理,镜像缓存版本更新也集成到了自动化部署流程中,非常好地解决我们ToB业务私有化部署的痛点。

节点组

如果对不同业务场景和资源使用方式,采用同一种管理方式,可能会造成资源调度的灵活性不足,扩展难和资源浪费等问题。我们在设计时抽象一层节点组来管理不同类型的资源。节点组维度配置资费模式(包年包月/按量计费/Spot竞价实例)、资费规格、芯片架构和区域,整合了云平台中多种实例类型,根据应用的特性调度不同类型的资源。所有节点组都会被统一管理,根据业务场景、资源规模进行调整优化。在应用性能和服务器成本之间达成一个平衡。

(1) 多种实例规格型号混用

云厂商提供的资源规格非常丰富,但是要合理搭配和使用才能花更小的成本产生更大的价值。得益于Kubernetes强大的兼容性和适配性。节点组可以让各种架构、厂商、规格、型号和版本的资源并存。不同的业务应用调度分配适合的资源类型。

比如有一些常规应用希望使用x86的服务器,而另外一些查询型应用希望使用ARM的服务器,并希望在同一套架构混合使用。通常来说ARM的服务器要比X86便宜约10%。而另外一些对安全和性能要求苛刻的应用,可以独立分配适量的资源。

(2) 资费模式混合

同一套架构为不同类型和使用场景的资源配置差异化的资费模式。例如,常驻留资源使用包年包月,弹性资源使用按量计费模式。程序的不同特性也可以选择是否采用Spot竞价模式。

(3) 多区域调度资源

同一个区域可能会出现特定型号资源存量不足,导致无法申请到资源。Trino云原生方案结合云服务功能打通各区域网络,将资源统一调度和使用整合到一个Kubernetes集群中。这样可以大幅提高资源申请成功率,确保在业务高峰时有充足的资源可供使用。

成本优化的思考

云厂商的资源使用资费模式有很多种类型(包年包月 / 按量计费 / Spot竞价实例 / 预留实例券 / 节省计划)。根据业务实际需求和场景综合使用可以节省比较多成本。

长驻留资源比较适合包年包月,弹性资源部分因为是只在高负载时按需使用,尽可能地使用按量计费模式。但是如果在按量计费模式下,每天时间超过8h,则需要重新计算成本。相同资源规格和使用时长计算的资费成本,按量计费比包年包月要贵一些。如果业务运行实例是无状态且偶发的,中断对业务的影响可以忽略,则可以使用Spot竞价实例模式。竞价计费模式通常比正常的资费要便宜很多,最低可达1折。如果能利用好这种计费模式,节省的服务器成本将相当可观。

利用节点组概念,来区分不同的资费类型。将不同的应用调度到不同的节点组。产生的资费也是按照不同节点组的实际使用情况来计算的。多种资源模式混合使用,将最大化地优化成本结构。

后续演进方向

目前的方案基本满足了大数据查询引擎资源弹性的诉求。不过也还面临着一些问题和挑战。

资源配置稳定性

Kubernetes 通过 HPA 来控制资源的弹性伸缩,如果配置不合理,很容易造成Pod的资源频繁的申请和释放。这会造成一定数量的中间态 Pod Terminating,导致整体架构的不稳定性。后续我们也将在资源控制的精确度上精进,让资源调度更加平稳顺滑,确保资源的生命周期管理有序、有效且合理。

业务价值

在上线云原生方案后基本实现了在业务上的资源隔离,多业务并行运行相互不影响。也可以很方便地支持更多业务和个性化需求的扩展。云原生方案的弹性伸缩能力,可以保证资源的按需使用。在月度硬件成本上下降了40%左右,服务的查询响应速度也提升50%左右。整个运维和治理过程也大大简化,方便后续的维护和管理。

后记

在架构的调研演进时,肯定会碰到各种各样的问题。保持心态的开放,加强与云厂商技术人员的沟通,不断拓展技术的边界,就能够不断深化解决方案的成熟度和完备性。在此,也要感谢腾讯云容器团队的大力支持。同时,对待未知、有待探索的技术领域,实践永远是验证想法和方案的唯一道路。我们一直在不断地探索和创新,期待与更多技术伙伴的交流和学习。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2023-03-28,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 腾讯云原生 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 背景
  • 设计思路
    • 弹性容器
    • 实现落地
      • 弹性容器资源
        • 服务接入
          • 镜象仓库
            • 镜像加速
              • 节点组
                • 成本优化的思考
                • 后续演进方向
                  • 资源配置稳定性
                  • 业务价值
                  • 后记
                  相关产品与服务
                  大数据
                  全栈大数据产品,面向海量数据场景,帮助您 “智理无数,心中有数”!
                  领券
                  问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档