作者:周涛 同程旅行数据中心大数据研发工程师
同程旅行是中国在线旅游行业的创新者和市场领导者。作为一家一站式平台,同程旅行致力于满足用户旅游需求,秉持 "让旅行更简单、更快乐" 的使命,主要通过包括微信小程序、APP、轻应用及其他渠道在内的线上平台,为用户提供几乎涵盖旅游所有方面的全面创新产品和服务选择,涵盖交通、住宿、景点门票预订及各种配套增值旅游产品及服务,旨在满足用户在整个旅途中不断变化的旅游需要。目前,同程旅行的月活跃用户已达到2亿多人。
为了提升数据分析查询性能,同时降低人力和硬件成本,公司的出行、住宿和公共等多个业务线都已接入并使用了 StarRocks 技术。
同程旅行有多年的 OLAP 使用经验,随着业务增长和变化,促使我们需要不断探索更合适的组件来满足需求。在这方面,StarRocks 作为一款优秀的数据库,在同程旅行的生产环境中得到了广泛应用,涵盖实时、离线和 Customer Data Platform(顾客数据平台,以下简称 CDP)等多个应用场景。
本文将从同程旅行 OLAP 平台演进、业务痛点和 StarRocks 是如何解决当前业务痛点这几个部分详细介绍 StarRocks 在同程旅行的生产落地实践。
同程旅行的 OLAP 平台演进
随着公司的业务变化和用户量的增加,数据量也在不断增加。数据分析场景变得越来越多样化,对实时分析的时效性要求也更高了。为了更好地满足这些需求,同程旅行的 OLAP 平台也在不断演进,整体的发展过程大致分为三个阶段:
第一阶段:以 Druid+Kylin 为基础构建的数据分析体系,满足了当时对于离线数据分析加速的需求,但在使用过程中也逐渐暴露出 SQL 分析、联邦查询、BI 兼容等方面能力不足与 CUBE 运维成本较高等一系列问题;
第二阶段(引入 StarRocks 前):在这一阶段,我们采用 ClickHouse+Greenplum 支撑实时、离线业务的分析处理,在一定程度上解决了上一阶段存在的问题;
第三阶段:由 StarRocks 作为统一的 OLAP 组件,减少多组件的维护压力。同时注重在企业内部与相关数据平台的集成,提升用户使用体验,降低用户组件使用和切换成本。
在说明我们为什么选择 StarRocks 作为我们新一代的 OLAP 组件前,我们需要先了解原有平台架构的不足:
-
ClickHouse:主要用于用户行为轨迹和订单实时数据存储和分析
-
Greenplum:主要用于公司内部的灵动分析看板,做分析报表使用
如上图所示,在原始架构中,对于实时场景,业务数据通过 Kafka 传入 Flink,在 Flink 中进行清洗、打宽表等逻辑处理,之后将结果数据导入 ClickHouse 中;对于离线场景,数据统一存储在 HDFS 中,通过 Hive+Spark 进行清洗处理后,将结果数据传入 Greenplum 中。
实时场景
主要涉及业务订单数据,数据可以通过前端用户埋点到 Kafka,或者订阅业务订单数据库 Binlog,实时写入到 MQ,然后使用 Flink SQL,关联维度表,将数据打宽,最后写入到 ClickHouse 中。
离线场景
将实时的用户埋点数据或订单库离线同步数据写入到 HDFS 中,然后经过离线调度做 ETL 数据清洗,再搬运到 ClickHouse 或 Greenplum 中。然而,在使用过程中,我们发现实时和离线分离架构存在一些问题:
-
分离架构导致开发使用极度不方便,且浪费计算存储资源;
-
组件技术栈不统一,导致业务人员需要熟悉多种语法;
-
多组件造成了极高的运维成本。
为解决在使用 ClickHouse、Greenplum 过程中遇到的性能、运维和成本等各方面的问题,我们进行了一些调研,开始对比和了解一些新的 OLAP 组件。接下来,我们将进一步说明使用 ClickHouse 和 Greenplum 架构所带来的业务痛点。通过这些问题的阐述,我们可以更好地理解为何需要寻找新的解决方案。
01 ClickHouse + Greenplum 架构带来的业务痛点
目前,同程 OLAP 组件被广泛使用,并已集成到实时开发平台、离线开发平台、灵动分析、数据地图和快速取数等多个平台系统中。在业务方面,主要涉及以下三类场景:
1.1 实时数据分析
在使用实时数据分析的业务场景,我们主要针对用户行为埋点、用户实时订单等数据进行冷热存储。实时热数据需要存储 30 天至一年不等的时间数据,用于高性能要求的实时统计分析;历史离线数据存储在 HDFS。在查询实时数据时,如果涉及多表关联或者关联历史数据时,当前组件性能无法满足,需要提前离线清洗,导致数据时效性较低。
1.2 灵动数据报表
在使用灵动数据报表的业务场景,用户在离线数仓中清洗出 DWD 或 ADS 层表,通过离线开发平台导入到 Greenplum 中,然后在灵动分析中配置数据集,以拖拉拽的形式生成看板,提供给分析决策使用。然而,在高峰时期,我们经常遇到查询速度慢甚至查询超时等问题,这给业务带来了困扰。
1.3 用户画像 & CDP
在用户画像和 CDP 的场景中,我们会根据用户基本信息、消费数据和行为数据等生成对应标签数据,以创建用户画像,并进行人群圈选和漏斗分析等。
之前我们使用了 ClickHouse 作为存储分析引擎,但随着 CDP 需求的变化,业务场景更加复杂,涉及到多表关联场景以及宽表和 BitMap 关联场景,用户对实时分析的查询性能提出了更高的要求。经过测试,ClickHouse 已无法很好的满足。
针对当前 ClickHouse+Greenplum 体系存在的各种问题,我们开始了基于 StarRocks 构建分析体系 3.0 阶段的升级演变。
StarRocks 在同程旅行的应用与实践
01 选择 StarRocks 的原因
为了解决上述问题,我们追求在新的 OLAP 组件中实现简单、高速和统一的特点(包括支持联邦分析)。为此,我们进行了 StarRocks、ClickHouse、Greenplum 和 Presto 等 OLAP 组件的比较。我们比较了数据摄入速度、查询性能、内存占用率、维护成本和易用性等指标。通过这些比较,我们希望找到最适合我们业务需求的 OLAP 组件。
下图展示了这些组件的具体比较结果:
-
查询性能优异:
StarRocks 是一款分布式列式存储分析数据库,它具有非常高的查询性能,尤其适用于实时数据分析和查询场景。与ClickHouse 相比,StarRocks 在多表联合查询方面表现更出色,尤其在 Primary Key 模型方面,其在实时动态更新和查询性能方面都表现优异。
-
维护难度低:
StarRocks 由 FE 和 BE 两类组件组成,不依赖于第三方组件,可以开箱即用。而且,StarRocks 具有良好的可扩展性,集群扩缩容方便,可以根据需求动态扩展集群规模,灵活提高系统性能。此外,数据可以在节点之间自动均衡,无需人为干预。
-
方便易用:
StarRocks 采用标准 SQL 协议且兼容 MySQL 协议,可以轻松集成到现有系统中。此外,在实时写入方面,官方也提供了 flink-connector-starrocks,写入可实现 exactly-once。另外,StarRocks 还具备方便的联邦查询功能,避免了数据搬运带来的资源消耗,从而提高了系统性能。
经过多方比较,我们最终选择了 StarRocks 作为统一的 OLAP 组件,并预计在未来逐步完成统一 OLAP 层的工作 。
02 StarRocks 的引入
同程旅行主要在以下三个场景中使用 StarRocks:实时数据分析、离线报表和 CDP 系统。
随着 StarRocks 的接入,新的数据应用流程架构如下:
2.1 使用 StarRocks 解决当前痛点
1)实时数据分析的整体时效性提升
在实时应用场景中,业务数据进入到 Kafka 或者 TurboMQ,然后通过 Flink 任务或 Flink SQL 任务进行业务计算转换,最终通过 flink-starrocks-connector 实时写入到 StarRocks,进行实时指标统计或者实时数据分析。实时链路中不再涉及关联打宽,缩短了链路,提升了整体的时效性。同时,StarRocks 采用星型模型组织数据,减少数据冗余存储。以下是我们实际中的一个 Flink SQL 案例:
通过将 StarRocks 集成到实时开发平台,用户可以轻松快速地将实时数据导入 StarRocks 并进行使用。
2)离线报表查询性能大幅提升
我们已经成功将 StarRocks 数据源集成到灵动分析系统中。现在可以将 StarRocks 中的表创建为灵动中的数据集,进行分析看板配置,并实时写入数据。此外,无需重复清洗,还可以直接进行报表配置。由于 StarRocks 支持标准 SQL 并兼容 MySQL 协议,因此系统集成 StarRocks 数据源非常便捷。切换引擎后,与 Presto 和 Greenplum 相比,报表查询性能大幅提升(在某些实际场景中,相较于 Greenplum,查询性能提升近一倍)。
下图是对 14 个 SQL 耗时进行统计对比:
3)CDP 系统查询效率提高
CDP 是一种数据管理平台,它可以集成多方数据,帮助企业更好地了解用户行为、喜好和需求,从而制定更加精准的运营策略。CDP 系统上线后,可以服务于公司各个事业部,对用户进行分层或保存人群进行运营,从而极大地提升了运营效率并降低了运营成本。
CDP 系统的具体工作流程如下:
1)数据导入:
当前先知系统有 1000 多个历史人群需要作为人群圈选的条件,而这 1000 多个人群数据的导入耗时较高,存在性能瓶颈。经过调研,使用以下方法可以很好的解决这个问题:
-
将 String 类型的用户 ID 转换成 Long 类型的 oneId;
-
然后通过 Spark 任务将 oneId 转换成 Java 代码的 BitmapValue 对象;
-
在所有的相同 key 的 BitMap 合并后,转换成 Base64string,这样将相同的 key 的数据合并成一条数据,导入到 StarRocks 中。
经过验证,采用以上方法可以大大提高数据导入性能,将 1.5 亿条数据的 10 个任务同时导入的耗时从 10 分钟以上下降到 10s 以内,并且可以减少导明细数据的集群资源消耗。
如上图所示,根据数据监控显示,红框内时间段是明细导入的网络传输量,而其他时间段为 BitMap 合并 Base64 后的传输量。这两者之间的传输量相差约 10 倍。针对这个问题,我们正在努力优化导入代码,并将其整理成 Demo,以便提交给社区供大家参考使用。
2)人群圈选:
接下来我们需要通过 BitMap 的函数操作,对用户选择的条件进行人群圈选。通过将条件组合成 StarRocks 对应的 BitMap 的 and、or、union 等函数,简单的查询可以在3秒以内得出结果。即使是复杂的(例如涉及宽表与多个 BitMap 表的关联查询)且数据量大的查询,也都可以在 10 秒以内得到结果。
3)人群保存:
这一步将圈选的结果人群 BitMap 转换成一个明细表,然后再通过 export 语句方式,将表的数据导入 HDFS 进行输出应用。
下述是实际应用中的人群分层迁移桑基图的 SQL 示例:
对应结果图:
该 SQL 中包含了 BitMap 与普通宽表的关联操作,以及三个亿级别大表的关联操作,整体可以在5至10秒内计算完成。
未来规划
-
更多业务场景推广落地
在公司内,我们将继续扩大和推广 StarRocks 的使用,以替换其他业务中遗留的 ClickHouse 和 Greenplum 组件,减少多组件的维护压力。同时注重在企业内部与相关数据平台的集成,提升用户使用体验,降低用户组件使用和切换成本。
-
上云
将 StarRocks 部署在公司的 Kubernetes 私有云中,以提高集群的扩展性和灵活性,并且可以依赖于 Kubernetes 的容错机制,自动监测和替换故障节点,提升集群可靠性和稳定性。目前,我们已经完成了开发,进行到了测试验证阶段。后续我们也将持续跟进测试 StarRocks 提供的云原生能力。
-
存算分离特性的使用
在离线报表应用中,我们计划测试使用即将推出的 3.x 版本。根据其存算分离的能力,在不降低查询性能的条件下,可以大大减少离线数据同步的工作量。
-
与社区共赢
我们将持续保持与社区的沟通,积极地将使用体验和性能测试反馈社区。通过与社区的合作,实现双赢的目标。