关于OceanBase中旁路导入的应用分享

news2024/9/22 13:42:38

背景

前段时间,在用户现场协助进行OceanBase的性能测试时,我注意到用户常常需要运用 insert into select 将上亿行的数据插入到一张大宽表里,这样的批量数据插入操作每次都需要耗时半个小时左右。对这一情况,我提议用户尝试采用旁路导入的方式,结果不到五分钟就就完成了相同数据量的导入。虽然当时我表面保持冷静,但内心却充满喜悦。用户方的DBA同事们也半开玩笑地表示:“看来我们即将失去因导入数据而赢得的咖啡时间红利了。”

昨晚负责旁路导入研发的剑鸣同学分享了一次关于旁路导入的技术讲座。我借此机会写了一篇学习笔记,详细梳理了旁路导入的大致思路,并总结了用户在使用过程中需要注意的要点。

​​​​​​​

设计思路

目前,OceanBase主流使用三种导入方式:load data、obloader 和 oms,这些方式都使用 insert 语句将数据写入 OceanBase。然而,使用 insert 语句写入数据需要经过 SQL、事务和存储。OceanBase 使用 LSM-Tree 结构进行存储。在这种存储结构中,insert 语句会先将数据写入内存表中,然后经过多轮转储和合并,才能最终存入最底层的 SSTable 中。这些过程消耗了大量的系统资源,特别是 CPU 资源,因此导入数据的速度不够理想。为了加快导入速度,我们采用了一种绕过中间步骤的技术,将需要导入的数据直接写入最底层的 SSTable 中,这种技术称为旁路导入。此外,旁路导入还可以用于加速一些需要大量写入 SQL 的操作,例如背景中提到的 insert into select 语句。旁路导入的语法详见官网中几个相关的语法,例如 load data。

1705632762

根据上图所示,数据导入可采用两种路径,上方深蓝色箭头所示的传统路径需要经过 SQL查询、事务处理、数据存储等一系列模块。而下方的浅蓝色箭头所示旁路导入路径主要是对导入的数据进行类型转换(按需),然后按照主键进行排序(按需),最后将排序后的数据写入到 major sstable 中。旁路导入是一条短路径,能减少不少系统资源消耗,加快导入速度。(上图中的 LSM-tree 指的是 Log-Structured Merge Tree, 一种基于内存和磁盘的数据结构,用于高效地插入、删除和查询大量数据。SSTable 指的是 Sorted String Table, 一种有序、持久化存储数据的数据结构,可支持高效的读写操作和范围查询。)

实现原理

现在的旁路导入是利用 DDL 来实现的,可以认为是一种特殊类型的 DDL。

所以主要的执行流程和 DDL 类似(DDL 的实现原理可以详见夏进的这篇博客《OceanBase Alter Table 原理介绍》),旁路导入的实现分为了几个步骤:

    1. 创建 hidden table,用于导入
    2. 给原表和 hidden table 加表锁
    3. 把原表的数据和新导入的数据合并后写入 hidden table 中
    4. 在 hidden table 中重建原表的索引和外键
    5. 交换原表和 hidden table 的 table_id(如果中间任何一步出现错误,不交换 table id 就可以保证原子性,只有当全部步骤都成功,才会交换 table id)
    6. 解表锁

如果原表不是空表,已经有一些数据了,就会把原表里的数据和导入数据一起整合到 hidden table 里面。

例如下图中 tablet 是原表的 tablet,tablet' 是 hidden table 的 tablet,旁路导入会把原表的 memtable、sstale,以及导入的数据一起归并到新的 hidden table 里。

1705632779

例如通过 load data 命令进行旁路导入,整体的数据流向是:类型转换、根据分区键转发到对应节点、在节点上按需进行排序,最后写入 major sstable。

1705632790

我们在这里还对数据类型转换的优化、数据排序、解析 csv 等过程都做了大量的优化。

对于数据类型转换:例如 csv 文件里的内容是 string,但是实际的列类型是 number(在 MySQL 模式下相当于 decimal),这时候就需要根据 number format 进行一个非常复杂的隐式类型转换,我们在这里对隐式类型转换中的 to_number 函数最常用的一些 number format 进行了非常极致的短路优化,性能比直接调用 to_number 能提升四五倍的样子。

对于数据的排序:因为 OB 都是索引组织表,所以如果对于无主键表,是不需要进行排序的(写入时一个隐藏的 increment pk 列会自动保证有序),直接写入 major sstable 就可以了,这也就是无主键表比有主键表的旁路导入速度还能再快上几倍的原因。对于有主键表,那就不得不按照主键进行排序了,如果输入的数据已经是有序的(例如 csv 文件中的数据就有序),我们还提供了一个选项,支持用户通过指定要导入的数据是否有序来决定能否进行优化,如果已经有序,内部就只会做归并排序。完全无序时才会走完整的排序流程,无序时为了充分利用内存资源,我们会对数据进行一个归并的外排,首先先利用最大可用内存对数据进行排序,然后落盘,最后再对磁盘上的各个有序的数据文件进行一个多线程的归并排序,这样不仅可以充分利用内存资源,还可以有效减少落盘的次数。

1705632806

其他的优化由于篇幅关系,这里就不再详细描述了。

使用时需要注意的一些地方

用户在日常使用中,如果不了解目前旁路导入一些要注意的地方,很可能会遇到各种问题,以下就是使用旁路导入时需要注意的几个点:

1. 旁路导入期间会加表锁,表无法被写入其他数据,整个过程中表是只读的。

2. 旁路导入的实现是 DDL 而非 DML,这点要特别留意!

(1)按理说 insert into select 可以在事务里面的,但是例如 Oracle 的 DDL 如果出现在事务中,就会在 DDL 执行结束之后提交事务,然后再继续处理事务中的后面的内容,DDL 类似于事务中的一个 barrier。因为 DDL 在事务中的特殊表现,所以我们暂时不支持旁路导入出现在多行事务中,只能出现在 autocommit 的单行事务中,否则会报错 not supported。

(2)还有一个要注意的点是 DDL 框架比较重,导入 1 行数据可能就需要 2s,所以不适合用于导入量特别小的数据(例如 100M 以下的数据)。

(3)由于 DDL 实现逻辑的限制(在 RS 上会有一段儿逻辑需要串行执行),暂时不能很好地支持大规模多条旁路导入并行。比如并发执行几百个普通的 insert into select 是没问题的,但是并发执行几百个旁路导入的 insert into select,可能就会有一堆 DDL 排队等着 RS 的调度了。

这几个点确实给使用上带来了一些麻烦,不过我们后面会把它的实现方式给改成 DML。

3. 功能上支持增量导入,但是性能上可能不会特别理想。因为旁路导入的目标表如果在导入前已有数据,那么已有数据会被重写一遍。如果导入一个已有数据量很大的表,增量需要把原来的数据重写一遍,这时候可能并不划算。

4.如果租户的内存特别大,或者说数据量比 memtable 还要小,那内存的 memtable 就能兜住全部要导入的数据,旁路导入可能就没啥优势了。因为旁路导入是要写磁盘的,肯定比不过只写内存不需要转储、合并的场景

5. 4.2 版本 lob 列还不支持走旁路导入,不过后面即将发布的 4.3 版本已经支持了。

6. 使用 INSERT INTO SELECT 语句旁路导入数据时,只支持 PDML(Parallel Data Manipulation Language,并行数据操纵语言),非 PDML 不能用旁路导入,详见官网。

总结

最后总结一下,OB 目前的旁路导入功能,最适用于:

  1. 大表的首次导入场景;
  2. 10 GB~TB 级别的数据迁移场景;
  3. 还有就是 CPU 和 内存都不是特别充裕的场景,因为旁路导入的执行路径很短,可以省掉非常多的 CPU 开销。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1534961.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

福建科立讯通信 指挥调度管理平台 SQL注入漏洞复现(CVE-2024-2620、CVE-2024-2621)

0x01 产品简介 福建科立讯通信指挥调度管理平台是一个专门针对通信行业的管理平台。该产品旨在提供高效的指挥调度和管理解决方案,以帮助通信运营商或相关机构实现更好的运营效率和服务质量。该平台提供强大的指挥调度功能,可以实时监控和管理通信网络设备、维护人员和工作任…

SpringMVC | Spring MVC中的“拦截器”

目录: 拦截器 :1. 拦截器的 “概述”2. 拦截器的 “定义” (创建“拦截器”对象)3. 拦截器的 “配置” (让“拦截器”对象生效)4. 拦截器的 “执行流程”“单个拦截器”的执行流程“多个拦截器”的执行流程 作者简介 :一只大皮卡丘,计算机专业…

python云上水果超市的设计与实现flask-django-php-nodejs

伴随着我国社会的发展,人民生活质量日益提高。于是对云上水果超市进行规范而严格是十分有必要的,所以许许多多的信息管理系统应运而生。此时单靠人力应对这些事务就显得有些力不从心了。所以本论文将设计一套云上水果超市,帮助商家进行商品信…

图论基础|深度优先dfs、广度优先bfs

dfs 与 bfs 区别 提到深度优先搜索(dfs),就不得不说和广度优先搜索(bfs)有什么区别 先来了解dfs的过程,很多录友可能对dfs(深度优先搜索),bfs(广度优先搜索…

几个常用的控件(2)

目录 一、单选按钮Radiobutton和RadioButtonList 1、Radiobutton控件 (1)button控制方式 (2)Radiobutton控制方式 2、RadiobuttonList控件 二、列表框ListBox和下拉列表DropdownList 1、ListBox 2、DropdownList 三、面板…

H3C技术大全复现之高级路由交换技术 1

华子目录 VLAN 基本技术VLANIEEE 802.1Q交换机端口类型MVRP协议实验测试 VLAN扩展技术Super VLAN产生背景Super vlan(相当于vlanif接口,也属于虚拟接口,可以充当网关)Sub vlan(普通vlan)关于代理ARP普通代理…

【c++入门】命名空间,缺省参数与函数重载

🔥个人主页: Quitecoder 🔥专栏:c笔记仓 朋友们大家好!本篇内容我们进入一个新的阶段,进入c的学习!希望我的博客内容能对你有帮助! 目录 1.c关键字2.第一个c代码3.命名空间3.1 nam…

python智慧农业小程序flask-django-php-nodejs

当今社会已经步入了科学技术进步和经济社会快速发展的新时期,国际信息和学术交流也不断加强,计算机技术对经济社会发展和人民生活改善的影响也日益突出,人类的生存和思考方式也产生了变化。传统智慧农业采取了人工的管理方法,但这…

导航栏还是侧栏?flutter 跨平台适配指南

介绍 引言:Flutter 的跨平台特性 Flutter 是由 Google 开发的一款跨平台应用开发框架,它具有许多优点,包括性能优异、开发效率高以及良好的用户体验等。其中,最引人注目的特性之一就是其出色的跨平台能力。通过编写一套代码&…

【SpringSecurity】十六、OAuth2.0授权服务器、资源服务器的配置(理论部分)

文章目录 0、OAuth2服务端结构1、授权服务配置2、授权服务器 ⇒ 配置客户端详情3、授权服务器 ⇒ 管理令牌配置4、授权服务器:配置端点访问的安全约束5、资源服务器配置 相关📕: 【OAuth2授权服务器配置完整Demo】 0、OAuth2服务端结构 OAu…

微信小程序分销返佣模式--小程序1-3级分销插件--小程序分销--

团购小程序是一种基于社区团购模式的电商平台,主要面向社区居民用户。 如果你想要开发一款分销团购小程序可以参考以下功能需求进行开发制作。 1、用户注册和登录 提供用户注册和登录功能,使用户能够创建和管理他们的账户。 2、会员管理 包括会员注…

sentinel使用控制台实现

1、添加依赖 <!--整合控制台--><dependency> <groupId>com.alibaba.csp</groupId> <artifactId>sentinel-transport-simple-http</artifactId> <version>1.8.0</version></dependency> 此项方法&#xff0…

【RPG Maker MV 仿新仙剑 战斗场景UI (六)】

RPG Maker MV 仿新仙剑 战斗场景UI 六 法术战斗窗口代码仿新仙剑效果 法术战斗窗口 这次来水点内容 由于之前已经做过了仿新仙剑的法术及物品窗口因此本次两篇内容&#xff0c;就来水点内容&#xff01;&#xff01;&#xff01; 由于帮助窗口之前已经做过&#xff0c;因此直接…

uniApp中使用小程序XR-Frame创建3D场景(1)环境搭建

1.XR-Frame简介 XR-Frame作为微信小程序官方推出的3D框架&#xff0c;是目前所有小程序平台中3D效果最好的一个&#xff0c;由于其本身针对微信小程序做了优化&#xff0c;在性能方面比其他第三方库都要高很多。 2.与Three.js的区别 做3D小程序的同学们对Three.js一定不陌生…

蓝桥杯STM32 G431 hal库开发速成——输入捕获

蓝桥杯的输入捕获较为简单&#xff0c;基本不涉及溢出的问题。所以这里就不介绍溢出了。文末有源码。 一、Cubemx配置 二、代码编写 1.在捕获回调函数中 void HAL_TIM_IC_CaptureCallback(TIM_HandleTypeDef *htim) {if(htim->InstanceTIM3){switch(count){case 1:{jishu1…

Mysql数据库的SQL语言详解

目录 一、数据库的基础操作 1、数据库的基本查看和切换 1.1 查看数据库信息 1.2 切换数据库 1.3 查看数据库中的表信息 1.4 查看数据库或数据库中表的结构&#xff08;字段&#xff09; 1.5 数据类型 1.5.1 整数型 1.5.2 浮点型(float和double) 1.5.3 定点数 1.5.4…

鸿蒙一次开发,多端部署(五)页面开发的一多能力介绍

本章介绍如何使用方舟开发框架“一多”能力&#xff0c;开发出在多设备上正常显示的页面。方舟开发框架推荐开发者使用声明式开发范式开发应用&#xff0c;故本章的内容和示例都主要基于声明式开发范式。本章主要包含如下内容&#xff1a; 布局能力 布局决定了页面中的元素按照…

Day75:WEB攻防-验证码安全篇接口滥用识别插件复用绕过宏命令填入滑块类

目录 图片验证码-识别插件-登录爆破&接口枚举 登录爆破 接口枚举 图片验证码-重复使用-某APP短信接口滥用 滑块验证码-宏命令-某Token&Sign&滑块案例 知识点&#xff1a; 1、验证码简单机制-验证码过于简单可爆破 2、验证码重复使用-验证码验证机制可绕过 3、…

九、C#桶排序算法

简介 桶排序是一种线性时间复杂度的排序算法&#xff0c;它将待排序的数据分到有限数量的桶中&#xff0c;每个桶再进行单独排序&#xff0c;最后将所有桶中的数据按顺序依次取出&#xff0c;即可得到排序结果。 实现原理 首先根据待排序数据&#xff0c;确定需要的桶的数量。…

pycharm中的Mark Directory As 里的 Sources Root、Excluded...

这里主要提到两个文件夹的作用&#xff0c;分别是Sources Root、Excluded 1、Sources Root 1、场景 平时使用pycharm&#xff0c;有时出现导包问题&#xff0c;将那个目录Mark Directory as sources root&#xff0c;然后就可以正常运行代码了 2、原理 其实主要就是将那个目录…