StarRocks关于ConcurrentModificationException 问题的解决
背景
本文基于 StarRocks 3.1.7
目前在基于Starrocks做一些数据分析的操作(主要是做一些简单的查询),同事遇到了一些并发的问题:
ontent:2024-11-27 07:04:34,048 WARN (starrocks-mysql-nio-pool-214933|3593819) [StmtExecutor.execute():643] execute Exception, sql SELECT distinct(id) FROM `db`.`table` WHERE col1='xxx' AND col2='xxx'
java.util.ConcurrentModificationException: nullat java.util.LinkedHashMap$LinkedHashIterator.nextNode(LinkedHashMap.java:719) ~[?:?]at java.util.LinkedHashMap$LinkedValueIterator.next(LinkedHashMap.java:746) ~[?:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalcUtils.deltaRows(StatisticsCalcUtils.java:176) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalcUtils.getTableRowCount(StatisticsCalcUtils.java:114) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalculator.computeOlapScanNode(StatisticsCalculator.java:257) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalculator.visitLogicalOlapScan(StatisticsCalculator.java:225) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalculator.visitLogicalOlapScan(StatisticsCalculator.java:161) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.operator.logical.LogicalOlapScanOperator.accept(LogicalOlapScanOperator.java:149) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.statistics.StatisticsCalculator.estimatorStats(StatisticsCalculator.java:177) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.task.DeriveStatsTask.execute(DeriveStatsTask.java:57) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.task.SeriallyTaskScheduler.executeTasks(SeriallyTaskScheduler.java:69) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.Optimizer.memoOptimize(Optimizer.java:595) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.Optimizer.optimizeByCost(Optimizer.java:201) ~[starrocks-fe.jar:?]at com.starrocks.sql.optimizer.Optimizer.optimize(Optimizer.java:134) ~[starrocks-fe.jar:?]at com.starrocks.sql.StatementPlanner.createQueryPlan(StatementPlanner.java:146) ~[starrocks-fe.jar:?]at com.starrocks.sql.StatementPlanner.planQuery(StatementPlanner.java:121) ~[starrocks-fe.jar:?]at com.starrocks.sql.StatementPlanner.plan(StatementPlanner.java:92) ~[starrocks-fe.jar:?]at com.starrocks.sql.StatementPlanner.plan(StatementPlanner.java:61) ~[starrocks-fe.jar:?]at com.starrocks.qe.StmtExecutor.execute(StmtExecutor.java:456) ~[starrocks-fe.jar:?]at com.starrocks.qe.ConnectProcessor.handleQuery(ConnectProcessor.java:392) ~[starrocks-fe.jar:?]at com.starrocks.qe.ConnectProcessor.dispatch(ConnectProcessor.java:506) ~[starrocks-fe.jar:?]at com.starrocks.qe.ConnectProcessor.processOnce(ConnectProcessor.java:782) ~[starrocks-fe.jar:?]at com.starrocks.mysql.nio.ReadListener.lambda$handleEvent$0(ReadListener.java:69) ~[starrocks-fe.jar:?]at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128) ~[?:?]at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628) ~[?:?]at java.lang.Thread.run(Thread.java:829) ~[?:?]
涉及到的表如下:
CREATE TABLE `table` (`id` bigint(20) NOT NULL ,`create_date` datetime NOT NULL ,`col1` varchar(64) NOT NULL ,`col2` varchar(20) NOT NULL
) ENGINE = OLAP PRIMARY KEY(`create_date`, `id`
) COMMENT ""
PARTITION BY date_trunc('month', create_date) DISTRIBUTED BY HASH(`id`) PROPERTIES ("replication_num" = "3", "in_memory" = "false", "enable_persistent_index" = "true", "replicated_storage" = "true", "partition_live_number" = "18", "compression" = "LZ4");
结论
StarRocks 对分区带有TTL的表,会后台启动线程轮询的去删除分区,轮询的间隔受到 dynamic_partition_check_interval_seconds 控制,
然而在查询的时候, Starrocks会做语法解析,以及基于CBO的优化,在这期间会统计涉及到的表的分区信息统计,而此时恰好遇到了后台线程的分区删除,导致了ConcurrentModificationException 并发异常。
目前可以参考这个issue ConcurrentModificationException when query during drop partition,以及 增大 dynamic_partition_check_interval_seconds(目前是10分钟) 这个参数来降低这种冲突的概率。
分析
这里主要涉及到两个部分:
一个部分是查询部分(主要是StmtExecutor.execute),一个是后台清理分区部分(DynamicPartitionScheduler)
查询部分
每个SQL查询都会经过 StmtExecutor.execute方法,进而生成物理执行计划,而在生成物理执行计划的阶段,会经过Optimizer 阶段,这个阶段由于默认情况下是基于CBO的优化,所以会统计涉及的表所扫描的数据量,最终会走到 StatisticsCalcUtils.deltaRows方法:
private static long deltaRows(Table table, long totalRowCount) {long tblRowCount = 0L;for (Partition partition : table.getPartitions()) {long partitionRowCount;TableStatistic tableStatistic = GlobalStateMgr.getCurrentStatisticStorage().getTableStatistic(table.getId(), partition.getId());if (tableStatistic.equals(TableStatistic.unknown())) {partitionRowCount = partition.getRowCount();} else {partitionRowCount = tableStatistic.getRowCount();}tblRowCount += partitionRowCount;}if (tblRowCount < totalRowCount) {return Math.max(1, (totalRowCount - tblRowCount) / table.getPartitions().size());} else {return 0;}}
这里会对 table.getPartitions 进行 迭代,也就是OlapTable的 idToPartition.valus 进行迭代, 注意 idToPartition 是HashMap类型的,
总体的流程如下:
StmtExecutor.execute||\/
StatementPlanner.plan||\/
StatementPlanner.planQuery||\/
StatementPlanner.createQueryPlan||\/
Optimizer.optimize||\/
Optimizer.optimizeByCost||\/
Optimizer.memoOptimize||\/
SeriallyTaskScheduler.executeTasks||\/
DeriveStatsTask.execute||\/
StatisticsCalculator.estimatorStats||\/
StatisticsCalculator.computeOlapScanNode||\/
StatisticsCalcUtils.getTableRowCount||\/
StatisticsCalcUtils.deltaRows
后台清理部分
对于这种带有TTL的分区表来说,会有 DynamicPartitionScheduler 这个后台线程进行分区的删除。具体代码见:
protected void runAfterCatalogReady() {if (!initialize) {// check Dynamic Partition tables only when FE startinitDynamicPartitionTable();}setInterval(Config.dynamic_partition_check_interval_seconds * 1000L);if (Config.dynamic_partition_enable) {executeDynamicPartition();}executePartitionTimeToLive();}
其中删除分区的频率就是由 Config.dynamic_partition_check_interval_seconds 也就是dynamic_partition_check_interval_seconds来决定的,
其中executeDynamicPartition方法就是执行分区删除,具体数据流如下 :
executeDynamicPartition||\/
executeDynamicPartitionForTable||\/
getDropPartitionClause||\/
GlobalStateMgr.getCurrentState().dropPartition(db, olapTable, dropPartitionClause);||\/
olapTable.dropPartition(db.getId(), partitionName, clause.isForceDrop());||\/
idToPartition.remove(partition.getId());
其中 在 executeDynamicPartitionForTable 中 RangePartitionInfo rangePartitionInfo = (RangePartitionInfo) olapTable.getPartitionInfo(); 会根据PartitionInfo的信息来进行判断,只有 RangePartitionInfo类型支持partition TTL删除,也就是Expression partitioning (recommended) 和Dynamic partitioning支持.
在最后的idToPartition.remove(partition.getId())中就会删除正在进行查询迭代的idToPartition.values,就是导致并发问题
相关文章:
StarRocks关于ConcurrentModificationException 问题的解决
背景 本文基于 StarRocks 3.1.7 目前在基于Starrocks做一些数据分析的操作(主要是做一些简单的查询),同事遇到了一些并发的问题: ontent:2024-11-27 07:04:34,048 WARN (starrocks-mysql-nio-pool-214933|3593819) [StmtExecutor.execute():643] execute Exceptio…...
网络安全防护指南:筑牢网络安全防线(5/10)
一、网络安全的基本概念 (一)网络的定义 网络是指由计算机或者其他信息终端及相关设备组成的按照一定的规则和程序对信息收集、存储、传输、交换、处理的系统。在当今数字化时代,网络已经成为人们生活和工作中不可或缺的一部分。它连接了世…...
替代FTP最佳跨网文件传输解决方案——FileLink
在传统的企业文件传输中,FTP(文件传输协议)曾因其便捷性和高效性被广泛应用。然而,其固有的安全漏洞、对大文件传输支持的局限性、易受网络攻击等问题,已逐渐暴露出FTP在现代企业环境下的不足。针对这一问题࿰…...
Cesium在vue2中的引入和注意事项
在Vue2中,可以使用npm包管理工具来安装Cesium,并通过import语句将其引入到项目中。下面是在Vue2中引入Cesium的步骤和注意事项: 步骤: 首先,打开终端并进入Vue项目的根目录。 运行以下命令来安装Cesium: …...
CentOS 9 配置静态IP
文章目录 1_问题原因2_nmcli 配置静态IP3_使用配置文件固定IP4_重启后存在的问题5_nmcli 补充 1_问题原因 CentOS 7 于 2014年6月发布,基于 RHEL 7,并在 2024年6月30日 结束维护。 CentOS 9 作为目前的最新版本,今天闲来闲来无事下载下来后…...
深入解析 Webhook:从原理到实践的全面指南
1. 引言 1.1 什么是 Webhook? Webhook 是一种基于 HTTP 回调的轻量级通信机制,它允许一个系统实时向另一个系统发送数据。当特定事件发生时,Webhook 会主动向指定的 URL 发送 HTTP 请求,通常携带事件相关的数据。这种被动接收通…...
基于springboot+vue实现的创新创业学分管理系统 (源码+L文+ppt)4-111
4 系统总体设计 4.1系统功能结构设计图 根据需求说明设计系统各功能模块。采用模块化设计方法实现一个复杂结构进行简化,分成一个个小的容易解决的板块,然后再将小的板块继续分化成功能单一的更小模块。模块化设计方法使测试调试、维护更容易ÿ…...
如何高效地架构一个Java项目
引言 Java是企业级应用开发的主流语言之一,而我们作为使用Java语言的程序员,职称有初级、中级、高级、资深、经理、架构,但我们往往只是慢慢通过经验的积累迭代了自己的等级,如果没有保持学习的习惯,大多数程序员会停留…...
Scala的模式匹配(8)
package hfdobject Test35_1 { //需求:现在有一个数组Array(1,2,3,4)。我希望能定义三个变量,他们的值分别是数组中的第1,2,3个元素的值 def main(args: Array[String]): Unit {val arr Array(1,2,3,4,5)//第一个元素的值:arr(0…...
nodejs30: CSS 剪辑路径clip-path导致伪元素不可见问题及解决方法
相关问题 应用圆角裁剪时无法显示::after 取消clip-path设置: 完整问题代码 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, i…...
Git分布式版本控制工具 Git基本概念、Git工作流程、Git常用命令、Git远程仓库、IDEA操作Git
目录 1.Git基本概念 1.1 概述 1.1.1 开发中的实际场景 1.1.2 版本控制器的方式 1.1.2.1 集中式版本控制工具(SVN) 1.1.2.2 分布式版本控制工具(Git) 2.概述git工作流程 3.Git常用命令 3.1 Git环境配置 3.1.1 下载与安装 3.1.2 基本配置 3.1.3 为常用指令配置别名&…...
十,[极客大挑战 2019]Secret File1
点击进入靶场 查看源代码 有个显眼的紫色文件夹,点击 点击secret看看 既然这样,那就回去查看源代码吧 好像没什么用 抓个包 得到一个文件名 404 如果包含"../"、"tp"、"input"或"data",则输出"…...
Android 获取数字键盘和输入类型
在Android中,获取数字键盘可以通过为EditText设置输入类型为number或numberPassword来实现。以下是一个简单的例子: <!-- 在XML布局文件中 --> <EditText android:id"id/editTextNumber" android:layout_width"match_parent…...
8. 一分钟读懂“代理模式”
8.1 模式介绍 代理模式是一种结构型设计模式,它通过提供一个代理对象来替代对另一个对象(真实对象)的访问。代理对象与真实对象实现相同的接口,并通过代理类对真实对象的访问进行控制,可以在调用前后执行附加操作&…...
【实战攻略】如何从零开始快速实现深度学习新想法?——四步走战略
标题 【实战攻略】如何从零开始快速实现深度学习新想法?——四步走战略 【核心结论】 通过四步走战略,即找到baseline论文、深入baseline代码、搭建自己的pipeline、融入核心算法,新手也能快速实现深度学习新想法。 【通俗解释࿰…...
Creating Server TCP listening socket *:6379: bind: No error
启动redis报错:Creating Server TCP listening socket *:6379: bind: No error 解决方案: 1、直接在命令行中输入 redis-cli.exe 2、输入shutdown,关闭 3、输exit,退出 4、重新输入 redis-server.exe redis.windows.conf&…...
Go热加载工具air-使用说明-win11问题解决指南
写web程序 每次都要ctrlc 然后go run .非常但疼 用一下这个热加载工具air Live reload for Go apps 贴个github地址:https://github.com/air-verse/air 1. go版本1.23先install一下 go install github.com/air-verse/airlatest下载完发现输入air windows还是报…...
华为HarmonyOS 让应用快速拥有账号能力 -- 2 获取用户头像昵称
场景介绍 如应用需要完善用户头像昵称信息,可使用Account Kit提供的头像昵称授权能力,用户允许应用获取头像昵称后,可快速完成个人信息填写。以下只针对Account kit提供的头像昵称授权能力进行介绍,若要获取头像还可通过场景化控…...
oracle表迁移至postgre
第一步: 导出表结构 进入脚本 第二步: 删除spool相关和prompt相关(不需要表空间的情况下) 类似以下语句 第三步: 修改数据类型 VARCHAR2 --> VARCHAR VARCHAR2(200 CHAR) --> VARCHAR(200) NUMBER(10,2) --> numeric(10,2…...
【PlantUML系列】类图(一)
目录 一、类 二、接口 三、抽象类 四、泛型类 五、类之间的关系 六、添加注释 七、包图 八、皮肤参数 一、类 使用class关键字定义类,类名后跟大括号,声明类的属性和方法。 属性:格式为{visibility} attributeName : AttributeType…...
蓝牙 BLE 扫描面试题大全(2):进阶面试题与实战演练
前文覆盖了 BLE 扫描的基础概念与经典问题蓝牙 BLE 扫描面试题大全(1):从基础到实战的深度解析-CSDN博客,但实际面试中,企业更关注候选人对复杂场景的应对能力(如多设备并发扫描、低功耗与高发现率的平衡)和前沿技术的…...
最新SpringBoot+SpringCloud+Nacos微服务框架分享
文章目录 前言一、服务规划二、架构核心1.cloud的pom2.gateway的异常handler3.gateway的filter4、admin的pom5、admin的登录核心 三、code-helper分享总结 前言 最近有个活蛮赶的,根据Excel列的需求预估的工时直接打骨折,不要问我为什么,主要…...
【HTML-16】深入理解HTML中的块元素与行内元素
HTML元素根据其显示特性可以分为两大类:块元素(Block-level Elements)和行内元素(Inline Elements)。理解这两者的区别对于构建良好的网页布局至关重要。本文将全面解析这两种元素的特性、区别以及实际应用场景。 1. 块元素(Block-level Elements) 1.1 基本特性 …...
LLM基础1_语言模型如何处理文本
基于GitHub项目:https://github.com/datawhalechina/llms-from-scratch-cn 工具介绍 tiktoken:OpenAI开发的专业"分词器" torch:Facebook开发的强力计算引擎,相当于超级计算器 理解词嵌入:给词语画"…...
【C++从零实现Json-Rpc框架】第六弹 —— 服务端模块划分
一、项目背景回顾 前五弹完成了Json-Rpc协议解析、请求处理、客户端调用等基础模块搭建。 本弹重点聚焦于服务端的模块划分与架构设计,提升代码结构的可维护性与扩展性。 二、服务端模块设计目标 高内聚低耦合:各模块职责清晰,便于独立开发…...
OpenLayers 分屏对比(地图联动)
注:当前使用的是 ol 5.3.0 版本,天地图使用的key请到天地图官网申请,并替换为自己的key 地图分屏对比在WebGIS开发中是很常见的功能,和卷帘图层不一样的是,分屏对比是在各个地图中添加相同或者不同的图层进行对比查看。…...
RNN避坑指南:从数学推导到LSTM/GRU工业级部署实战流程
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文全面剖析RNN核心原理,深入讲解梯度消失/爆炸问题,并通过LSTM/GRU结构实现解决方案,提供时间序列预测和文本生成…...
处理vxe-table 表尾数据是单独一个接口,表格tableData数据更新后,需要点击两下,表尾才是正确的
修改bug思路: 分别把 tabledata 和 表尾相关数据 console.log() 发现 更新数据先后顺序不对 settimeout延迟查询表格接口 ——测试可行 升级↑:async await 等接口返回后再开始下一个接口查询 ________________________________________________________…...
从“安全密码”到测试体系:Gitee Test 赋能关键领域软件质量保障
关键领域软件测试的"安全密码":Gitee Test如何破解行业痛点 在数字化浪潮席卷全球的今天,软件系统已成为国家关键领域的"神经中枢"。从国防军工到能源电力,从金融交易到交通管控,这些关乎国计民生的关键领域…...
ubuntu22.04有线网络无法连接,图标也没了
今天突然无法有线网络无法连接任何设备,并且图标都没了 错误案例 往上一顿搜索,试了很多博客都不行,比如 Ubuntu22.04右上角网络图标消失 最后解决的办法 下载网卡驱动,重新安装 操作步骤 查看自己网卡的型号 lspci | gre…...
