StarRocks 存算分离 Compaction 原理
前言
StarRocks 中每次数据摄入都会生成一个新的数据版本,而查询时需要将所有版本数据进行合并才能获得一个正确的结果,如果历史数据版本太多,那么查询时需要读取的文件数也会很多,造成查询效率低下。因而 StarRocks 存在内部任务定期将历史数据版本进行整合,消除重复数据记录,我们称之为 Compaction。
Compaction 是为了将不同版本的数据文件进行整合,合并成大文件的动作,减少系统中小文件数量,进而提升查询效率。相比于存算一体表,StarRocks 存算分离实现了新的 Compaction 调度机制,表现为:
- Compaction 调度由 FE 发起,BE执行。FE 按照 Partition 为单位来发起 Compaction 任务
 - Compaction 会生成一个新版本,也走导入的写数据、commit、publish version 这套完整流程
 
本文旨在描述 StarRocks 存算分离表 Compaction 基本实现原理,帮助开发和运维人员能更好地理解并根据实际需要调整 Compaction 相关配置,以在实践中取得更好地效果。
背景介绍
前面说过,每次导入都会在 FE 内生成一个新版本,而该版本被标记在 Partition 之上。一旦导入事务成功提交,便会更新 Partition 的可见数据版本号,Partition 的数据版本号单调递增。
需要注意的是,一个 Partition 内可能存在多个 Tablet,这些 Tablet 都共享相同的数据版本号,即使一次导入可能只涉及其中部分 Tablet,一旦导入事务成功提交,Partition 下所有的 Tablet 的版本都会相应地得到提升。

例如上图中,Partition X 内含 Tablet 1 ~ N,当前的可见版本为12,一旦产生新的导入事务 New Load Txn,且该事务成功提交,那么 Partition X 的可见版本就变成了 13。
基本框架
StarRocks 存算分离表 Compaction 由两个角色组成:调度者(Compaction Scheduer)和执行者(Compaction Executor)。调度者通过 RPC 发起 Compaction 任务(Compaction Job),而执行者负责执行 Compaction Job。
在 StarRocks 存算分离中,FE 作为 Compaction Scheduler,而 BE 或者 CN 都作为 Compaction Executor。每个 Compaction Excutor 内都存在一个线程池专门用于执行 Compaction Job。

Compaction Scheduer 调度
FE 上存在一个周期性运行线程 Compaction Scheduer,负责调度发起所有的 Compaction Task。FE 以 Partition 为调度的基本单位。
FE 上掌握了每个 Partition 的 Compaction Score 信息,该信息用来表示 Partition 内所有 Tablet 的需要进行 Compaction 的优先级,Compaction Score 越高,表示 Partition 需要合并的紧急程度越高。
每次 Compaction Scheduer 线程运行时,会挑选出当前 Compaction Score 最高的 Partition,并为这些 Partition 构造 Compaction Task。当然,Compaction Scheduer 也会控制每次最多发起的 Compaction Task 数量。
构造 Compaction Task 的逻辑相对比较简单,对于每个 Partition,Scheduler 会获得其所有的 Tablet,然后为每个 CN 构造一个 Compaction Task,Task 内包含需要在该 CN 上执行 Compaction 任务的 Tablet 列表,然后发送 Task 给 CN 节点。
整个流程如下图所示:

在上图中,FE 上存在两个 Partition 需要执行 Compaction,分别为 Partition X 和 Partition Y。Partition X 内含4个 Tablet(1 ~ 4),而 Partition Y 内含3个 Tablet(5~7)。
Scheduer 通过计算发现:
Partition X 内,Tablet-2 和 Tablet-4 位于相同的 CN-1,而 Tablet-1 和 Tablet-3 位于相同的 CN-2,于是为 Partition X 构造了两个 Compaction Task(Task-1 与 Task-2),其中 Task-1 内包含 Tablet-2 和 Tablet-4,而 Task-2 内包含 Tablet-1 和 Tablet-3。
Partition Y 内,Tablet-5 和 Tablet-7 位于相同的 CN-1,而 Tablet-6 位于另外一个CN-2,于是为 Partition Y 也构造了两个 Compaction Task(Task-3 与 Task-4),其中 Task-3 内包含 Tablet-5 和 Tablet-7,而 Task-4 内包含 Tablet-6。
最终,每个 Task 被发往自己所属的 CN。
Compaction Executor 执行 Task
前面说过,FE 的 Compaction Scheduler 生成 Compaction Task,并发往 CN / BE 节点。CN / BE 节点上存在专有线程池来处理这些 Task,且线程池数量可配置(即将支持动态配置)。每个线程会从 Compaction Task 任务队列中获取下一个要被执行的 Task。
所谓 Compaction,其本质是将多个数据文件进行整理合并,删除其中的重复记录,并形成一个更大的数据文件。如下图所示:

例如上图中,version 1 和 version 2 数据文件进行 Compaction 后,消除了 version 1 中的旧版本数据(id = 2, value = 11, id = 5, value = 30),最终生成了新的数据版本文件 version 3。
Compaction 后的数据清理
目前 StarRocks 存算分离表使用了数据多版本技术,整体上的存储结构如下图所示:

上图中共产生了三次数据导入事务,其中:
- Load Txn 1: 在事务数据写入阶段,生成了新数据文件 file 1 & file 2,且该事务提交后生成了 Tablet Meta V1,其中记录该版本可见的文件列表为 {file-1, file-2}
 - Load Txn 2: 在事务数据写入阶段,生成了新数据文件 file 3 & file 4。在提交时,根据前一个版本(即 Tablet Meta V1)然后加上本次导入事务生成的新数据文件(file-3 & file-4),生成了新的 Tablet Meta V2,因此,该版本可见的文件列表为 {file-1, file-2, file-3, file-4}
 - Load Txn 3: 在事务写入阶段,产生了新数据文件 file 5。该事务提交时,根据前一个版本(即 Tablet Meta V2)然后加上本次导入事务生成的新数据文件(file-5),产生了新的 Tablet Meta V3,因此,该版本的可见文件列表为 {file-1, file-2, file-3, file-4, file-5}
 
除了用户导入事务产生了新的数据版本,在存算分离表中,系统后台 Compaction 任务也会产生新数据版本。Compaction 的目的有二: 1). 将多个版本的小文件合并为大文件,减少查询时的随机 IO 次数,2). 消除重复数据记录,减少数据总量。
在存算分离表中,每次 Compaction 也会产生一个全新的版本。依然以上面为例,假如在上面 Txn 3 之后新的事务 Txn 4 为一次 Compaction 任务,并且将 file1 ~ file4 这4个文件合并成为 file-6,那么该事务提交时,生成的新版本 Tablet Meta V4 内记录的文件列表为 {file-5, file-6}。

观察上例并思考可知,如果系统在运行过程中一直不会进行 Compaction。那么系统中的数据文永远也无法被删除。试想上例中我们可以将 Tablet Meta V1,Tablet Meta V2 文件删除,但我们无法删除 file-1、file-2、file-3 以及 file-4,因为这些文件依然被 Tablet Meta V3 所引用。
但有了数据合并(Compaction)后,情况就变得不一样了。上例中,由于发生了一次 Compaction(上图中的 Compact Txn 4),将 file-1、file-2、file-3、file-4 合并生成了新文件 file-6 并生成了新的 Tablet Meta V4,由于 file-1 至 file-4 中的内容已经在 file-6 中存在,因而,一旦版本 V1、V2、V3 不再被访问,file-1 至 file-4 便可以被安全删除。此时的数据版本情况如下图所示:

因此,综合上面的讨论,我们可以发现,只有在 Compaction 完成后原始的数据文件方可被删除。因而,判断数据文件能否安全删除的最直观的规则是:该数据文件不再被任何 Tablet Meta 所引用。
相关文章:
StarRocks 存算分离 Compaction 原理
前言 StarRocks 中每次数据摄入都会生成一个新的数据版本,而查询时需要将所有版本数据进行合并才能获得一个正确的结果,如果历史数据版本太多,那么查询时需要读取的文件数也会很多,造成查询效率低下。因而 StarRocks 存在内部任务…...
搭建ELK日志采集与分析系统
SpringCloud微服务实战——企业级开发框架 💝💝💝欢迎来到我的博客,很高兴能够在这里和您见面!希望您在这里可以感受到一份轻松愉快的氛围,不仅可以获得有趣的内容和知识,也可以畅所欲言、分享您…...
java集合中自动排序的treeset和treemap
底层 TreeSet 和 TreeMap 的底层架构都是基于红黑树实现的。红黑树是一种自平衡的二叉搜索树,其特性保证了插入、删除和查找操作的时间复杂度为 (O( log  n \log n logn)),无论数据量多大,操作性能都能保持在合理的范围内。 1. 红黑树概述 红黑树是一种平衡二叉搜索树(…...
Android 修改SystemUI 音量条的声音进度条样式
一、前言 Android System UI 开发经常会遇到修改音量进度条样式的需求,主要涉及的类有VolumeDialogImpl与xml文件,接下来会逐步实现流程。先看看效果。 修改前 修改后 二、找到对应类 通过aidegen 打断点调试对应代码类VolumeDialogImpl定位到volume_d…...
电商场景的视频生成的prompt测评集合
1.收集的一些提示词 一台写着Vidu的赛车在路上飞驰,赛车上面坐着一只乌龟 一个宇航员在太空中骑单车 两个巨大的机器人在打架,电影风格,史诗感,高细节 在科幻电影风格中,两个巨大的机器人在城市废墟中激烈战斗。使用高角度俯拍,展现机器人的宏伟和战斗的史诗感。机器人…...
day34
1 非阻塞型IO 让我们的read函数不再阻塞,无论是否读取到消息,立刻返回 1.1 fcntl函数 原型:int fcntl(int fd, int cmd, ... /* arg */ ); 调用:int flag fcntl(描述符,F_GETFL) fcntl(描述符,F_SETFL&am…...
无缝融入,即刻智能[三]:Dify-LLM平台知识库构建(多路召回、精排重排),43K+星标见证专属智能方案
无缝融入,即刻智能[三]:Dify-LLM平台知识库构建(多路召回、精排重排),43K+星标见证专属智能方案 大语言模型的训练数据一般基于公开的数据,且每一次训练需要消耗大量算力,这意味着模型的知识一般不会包含私有领域的知识,同时在公开知识领域存在一定的滞后性。为了解决这一…...
AWS服务WAF
在 AWS 中使用 Web Application Firewall (WAF) 来防御常见的攻击手段,如 DDoS 攻击和 SQL 注入攻击,可以通过创建和配置规则来实现。下面是如何使用 AWS WAF 阻止这些常见攻击的详细操作步骤。 1. 登录到 AWS 管理控制台 打开 AWS 管理控制台。使用你…...
二叉树中的奇偶树问题
目录 一题目: 二思路汇总: 1.二叉树层序遍历: 1.1题目介绍: 1.2 解答代码(c版): 1.3 解答代码(c版): 1.4 小结一下: 2.奇偶树分析…...
GD - EmbeddedBuilder - 用DMA进行串口发送接收,支持接收不定长包
文章目录 GD - EmbeddedBuilder - 用DMA进行串口发送接收,支持接收不定长包概述笔记硬件连接图形化配置485EN的配置串口的图形化配置 代码实现main.cgd32f3x0_hal_it.cgd32f3x0_hal_init.cgd32f3x0_hal_init.hgd32f3x0_hal_it.hgd32f3x0_libopt.h 备注END GD - Embe…...
英语中apartment(公寓)(美式)、house(房子)、flat(公寓)(英式)、villa(别墅)、room(房间)区别
文章目录 英语中apartment、house、flat、villa、room区别 英语中apartment、house、flat、villa、room区别 在英语中,“apartment”、“house”、“flat”、“villa”、和 “room” 这些词语都与居住空间有关,但它们各自的含义和用途有所不同ÿ…...
黑马头条vue2.0项目实战(十一)——功能优化(组件缓存、响应拦截器、路由跳转与权限管理)
1. 组件缓存 1.1 介绍 先来看一个问题? 从首页切换到我的,再从我的回到首页,我们发现首页重新渲染原来的状态没有了。 首先,这是正常的状态,并非问题,路由在切换的时候会销毁切出去的页面组件ÿ…...
《AI视频类工具之一—— 即创》
一.简介 官网:即创 - 一站式智能创意生产与管理平台 即创是字节跳动(现更名为抖音集团)旗下的一款一站式智能创意生产与管理平台,旨在帮助用户高效地进行创意内容的生成、管理和分析。 二.功能介绍 视频创作: 智能成片:利用AI技术自动编辑视频片段,快速生成完整的视频…...
CSS的:host伪类:精确定位于Web组件的指南
随着Web组件技术的发展,自定义元素(Custom Elements)已经成为现代Web开发中不可或缺的一部分。CSS的:host伪类为Web组件的样式封装提供了一种强大的工具,它允许开发者为自定义Web组件的宿主元素定义样式。本文将详细介绍:host伪类…...
安卓sdk manager下载安装
安卓sdk下载安装 android SDK manager下载 环境变量配置 ANDROID_HOME:D:\Android %ANDROID_HOME%\tools %ANDROID_HOME%\platform-tools %ANDROID_HOME%\build-tools\29.0.3Android SDK Platform-tools公用开发工具包,需要下载 Android SDK Tools基础…...
CV学习笔记3-图像特征提取
图像特征提取是计算机视觉中的一个关键步骤,其目标是从图像中提取有意义的特征,以便进行进一步的分析或任务,如分类、检测、分割等。特征提取可以帮助减少数据的维度,同时保留重要的信息。以下是常见的图像特征提取方法和技术&…...
Git使用方法(三)---简洁版上传git代码
1 默认已经装了sshWindows下安装SSH详细介绍-CSDN博客 2 配置链接github的SSH秘钥 1 我的.ssh路径 2 进入路径cd .ssh 文件 3 生成密钥对 ssh-keygen -t rsa -b 4096 (-t 秘钥类型 -b 生成大小) 输入完会出现 Enter file in which to save the key (/c/Users/Administrator/…...
8.21-部署eleme项目
1.设置主从从mysql57服务器 (1)配置主数据库 [rootmsater_5 ~]# systemctl stop firewalld[rootmsater_5 ~]# setenforce 0[rootmsater_5 ~]# systemctl disable firewalldRemoved symlink /etc/systemd/system/multi-user.target.wants/firewalld.serv…...
多目标跟踪之ByteTrack论文(翻译+精读)
ByteTrack:通过关联每个检测框进行多对象跟踪 摘要 翻译 多对象跟踪(MOT)旨在估计视频中对象的边界框和身份。大多数方法通过关联分数高于阈值的检测框来获取身份。检测分数低的物体,例如被遮挡的物体被简单地丢弃,…...
【实践】Java开发常用工具类或中间件
在Java开发中,有许多常用的工具类和中间件,它们可以显著提高开发效率,简化代码,并提供强大的功能。这些工具类和中间件广泛应用于各种类型的Java应用程序中,包括Web应用、企业级应用、微服务等。以下是一些在Java开发中…...
使用VSCode开发Django指南
使用VSCode开发Django指南 一、概述 Django 是一个高级 Python 框架,专为快速、安全和可扩展的 Web 开发而设计。Django 包含对 URL 路由、页面模板和数据处理的丰富支持。 本文将创建一个简单的 Django 应用,其中包含三个使用通用基本模板的页面。在此…...
C# 类和继承(抽象类)
抽象类 抽象类是指设计为被继承的类。抽象类只能被用作其他类的基类。 不能创建抽象类的实例。抽象类使用abstract修饰符声明。 抽象类可以包含抽象成员或普通的非抽象成员。抽象类的成员可以是抽象成员和普通带 实现的成员的任意组合。抽象类自己可以派生自另一个抽象类。例…...
Ascend NPU上适配Step-Audio模型
1 概述 1.1 简述 Step-Audio 是业界首个集语音理解与生成控制一体化的产品级开源实时语音对话系统,支持多语言对话(如 中文,英文,日语),语音情感(如 开心,悲伤)&#x…...
涂鸦T5AI手搓语音、emoji、otto机器人从入门到实战
“🤖手搓TuyaAI语音指令 😍秒变表情包大师,让萌系Otto机器人🔥玩出智能新花样!开整!” 🤖 Otto机器人 → 直接点明主体 手搓TuyaAI语音 → 强调 自主编程/自定义 语音控制(TuyaAI…...
css3笔记 (1) 自用
outline: none 用于移除元素获得焦点时默认的轮廓线 broder:0 用于移除边框 font-size:0 用于设置字体不显示 list-style: none 消除<li> 标签默认样式 margin: xx auto 版心居中 width:100% 通栏 vertical-align 作用于行内元素 / 表格单元格ÿ…...
力扣-35.搜索插入位置
题目描述 给定一个排序数组和一个目标值,在数组中找到目标值,并返回其索引。如果目标值不存在于数组中,返回它将会被按顺序插入的位置。 请必须使用时间复杂度为 O(log n) 的算法。 class Solution {public int searchInsert(int[] nums, …...
比较数据迁移后MySQL数据库和OceanBase数据仓库中的表
设计一个MySQL数据库和OceanBase数据仓库的表数据比较的详细程序流程,两张表是相同的结构,都有整型主键id字段,需要每次从数据库分批取得2000条数据,用于比较,比较操作的同时可以再取2000条数据,等上一次比较完成之后,开始比较,直到比较完所有的数据。比较操作需要比较…...
给网站添加live2d看板娘
给网站添加live2d看板娘 参考文献: stevenjoezhang/live2d-widget: 把萌萌哒的看板娘抱回家 (ノ≧∇≦)ノ | Live2D widget for web platformEikanya/Live2d-model: Live2d model collectionzenghongtu/live2d-model-assets 前言 网站环境如下,文章也主…...
Axure 下拉框联动
实现选省、选完省之后选对应省份下的市区...
用递归算法解锁「子集」问题 —— LeetCode 78题解析
文章目录 一、题目介绍二、递归思路详解:从决策树开始理解三、解法一:二叉决策树 DFS四、解法二:组合式回溯写法(推荐)五、解法对比 递归算法是编程中一种非常强大且常见的思想,它能够优雅地解决很多复杂的…...
