表压缩函数提问

【 使用环境 】 测试环境
【 OB or 其他组件 】OB
【 使用版本 】OB4.2.4
【问题描述】建表用的是默认压缩方式是zstd_1.3.8,抓火焰图发现,DAG线程和MINOR_EXE线程实际执行的是lz4的压缩解压缩函数,想问下这是为什么

@论坛小助手

根据文档库中的信息,可以对您的问题进行如下分析和解答:

1. 默认压缩方式

在 OceanBase 数据库中,表的默认压缩方式由参数 default_compress_func 控制,默认值为 zstd_1.3.8(文档片段 2)。这意味着在创建表时,如果没有显式指定压缩算法,OceanBase 会使用 zstd_1.3.8 对数据进行压缩。

2. 压缩算法的实际执行

尽管表的默认压缩方式是 zstd_1.3.8,但在某些场景下,实际执行的压缩解压函数可能是其他算法(如 lz4)。这种现象可能与以下因素有关:

(1) 日志传输压缩

  • 参数 log_transport_compress_func 控制事务日志内部传输时使用的压缩算法,默认值为 lz4_1.0(文档片段 7 和 文档片段 1)。
  • 在事务处理过程中,DAG 线程和 MINOR_EXE 线程可能会涉及事务日志的生成和传输。因此,即使表的压缩方式是 zstd_1.3.8,这些线程仍可能使用 lz4 进行日志传输的压缩和解压。

(2) 临时数据的压缩

  • 在执行查询或写入操作时,OceanBase 可能会生成一些临时数据(如 Minor Freeze 阶段的增量数据)。这些临时数据的压缩算法可能并不完全依赖于表的默认压缩方式,而是由系统内部的优化策略决定。
  • 例如,lz4 的压缩速度较快,适合用于需要快速处理的临时数据场景。

(3) 性能优化

  • OceanBase 数据库在设计上会根据不同的场景选择最适合的压缩算法。虽然 zstd_1.3.8 提供了较高的压缩率,但其压缩和解压速度相对较慢。在某些高性能要求的场景下,系统可能会优先选择速度更快的 lz4 算法。

3. 验证方法

如果您希望进一步确认为何实际执行的是 lz4 压缩解压函数,可以通过以下步骤进行验证:

  • 检查租户级参数 log_transport_compress_func 的值,确认是否为 lz4_1.0
  • 查看火焰图中具体调用栈的信息,判断是否与事务日志传输相关。
  • 如果需要强制使用 zstd_1.3.8,可以尝试调整相关参数或优化查询逻辑。

4. 总结

实际执行的压缩解压函数可能因场景不同而异。在您的环境中,DAG 线程和 MINOR_EXE 线程实际执行的是 lz4 压缩解压函数,这很可能是由于事务日志传输或临时数据处理的需求所致。这种行为属于 OceanBase 数据库的正常优化策略,并不意味着表的默认压缩方式发生了变化。

如果仍有疑问,建议联系 OceanBase 的技术支持团队以获取更详细的解答。

更多信息请查看:

  1. 集群管理 FAQ
  2. 合并管理概述
  3. clog_persistence_compress_func
  4. 表压缩
  5. 数据压缩概述
  6. 压缩与编码
  7. clog_transport_compress_func
  8. default_compress_func
  9. 通用语法
  10. enable_clog_persistence_compress

image
火焰图这一块,都是微块在做压缩,不涉及日志哈

对压缩可以理解有两个部分

  1. 写入需要压缩, ob内部所有数据是通过compaction写入, 因此也在这里做压缩
  2. 读取需要解压, 所有压缩数据读取后要解压, 这里会发生在后台io或者前台同步io
  1. 写入需要压缩, ob内部所有数据是通过compaction写入, 因此也在这里做压缩
  2. 读取需要解压, 所有压缩数据读取后要解压, 这里会发生在后台io或者前台同步io @论坛小助手

根据您提供的火焰图信息以及描述,可以进一步分析为什么在 OceanBase 4.2.4 中,尽管表的默认压缩方式是 zstd_1.3.8,但在实际执行中,DAG 线程和 MINOR_EXE 线程却使用了 lz4 的压缩解压函数。


分析与解答

1. 微块压缩的实际行为

从火焰图中可以看出,涉及的模块主要是 blocksstable::ObMicroBlockcompaction 相关的逻辑。这表明当前的行为发生在微块(Micro Block)的压缩和解压过程中。以下是关键点:

  • OceanBase 的微块压缩机制
    在 OceanBase 数据库中,数据是以微块为单位进行存储和管理的,默认微块大小为 16KB。对于微块的压缩,系统可能会根据性能优化策略选择不同的压缩算法。

  • 压缩算法的选择依据
    尽管表级别的默认压缩方式是 zstd_1.3.8,但微块的压缩可能并不完全依赖于表的设置。具体原因如下:

    • 性能优化lz4 的压缩和解压速度非常快,适合高频操作场景(如 Minor Freeze 阶段的增量数据写入)。因此,在某些内部实现中,OceanBase 可能会优先选择 lz4 来处理微块的压缩和解压。
    • 临时数据处理:在 Compaction(合并)过程中,生成的中间数据可能需要快速压缩和解压,此时也会倾向于使用 lz4

2. 火焰图中的关键信息

火焰图显示了以下调用栈:

  • oceanbase::blocksstable::ObMacroBlockWriter::append_row
  • oceanbase::compaction::ObPartitionMinorMerger::inner_process

这些调用栈表明当前的操作与微块写入和 Minor Merge(小合并)相关。在这些场景下,OceanBase 的实现可能会优先选择性能更高的压缩算法(如 lz4),而不是严格遵循表级别的默认压缩方式。

3. 为什么选择了 lz4

根据文档片段中的信息(文档片段 4 和 文档片段 5),lz4snappy 的压缩速度较快,但压缩率较低。相比之下,zstdzlib 提供了更高的压缩率,但压缩和解压速度较慢。因此,OceanBase 在以下场景中可能会选择 lz4

  • 高频写入场景:如 Minor Freeze 阶段的增量数据写入。
  • Compaction 过程中的临时数据处理:为了加快合并速度,系统可能会选择更快的压缩算法。

4. 表压缩方式与微块压缩的关系

虽然表的默认压缩方式是 zstd_1.3.8,但这仅影响最终存储到磁盘上的数据块(Macro Block)的压缩方式。而在微块层面,OceanBase 的实现可能会根据具体的场景选择更适合的压缩算法。这种设计是为了平衡性能和存储空间利用率。


总结

在您的环境中,DAG 线程和 MINOR_EXE 线程实际执行的是 lz4 压缩解压函数,这是由于以下原因:

  1. 微块的压缩和解压可能不完全依赖于表的默认压缩方式。
  2. 在高频写入或 Compaction 场景中,OceanBase 会选择性能更高的压缩算法(如 lz4)以优化性能。
  3. 这种行为属于 OceanBase 数据库的正常优化策略,并不意味着表的默认压缩方式发生了变化。

如果您希望进一步确认这一行为,可以通过以下方法验证:

  • 检查 default_compress_func 参数的值,确认表的默认压缩方式是否为 zstd_1.3.8
  • 使用 EXPLAIN 或其他诊断工具查看具体查询的执行计划,分析是否涉及 Compaction 或高频写入场景。

如果仍有疑问,建议联系 OceanBase 的技术支持团队以获取更详细的解答。

检索到的文档如下:

  1. 表压缩
  2. default_compress_func
  3. 压缩与编码
  4. 合并管理概述
  5. 数据压缩概述
  6. 集群管理 FAQ
  7. clog_persistence_compress_func
  8. clog_transport_compress_func

根据文档库中的信息,OceanBase 数据库在数据写入和读取时的压缩与解压机制如下:

  1. 写入时的压缩

OceanBase 数据库采用 LSM-Tree 架构,在数据写入过程中,MemTable 中的数据达到一定阈值或触发每日合并时会转储/合并到磁盘上形成 SSTable。这一过程发生在 Compaction 阶段,因此所有的数据压缩操作也在此阶段完成(参考片段标题:压缩与编码)。您可以配置参数 default_compress_func 来选择具体的压缩算法,默认值为 zstd_1.3.8(参考片段标题:合并管理概述 → 合并的压缩算法)。

  1. 读取时的解压

当从 SSTable 中读取数据时,如果数据被压缩,则需要进行解压操作。解压可能发生在后台异步 IO 或前台同步 IO 中(参考片段标题:压缩与编码)。具体来说:

  • 如果数据是通过后台线程预读取的,则解压会在后台异步 IO 中完成。

  • 如果数据是按需读取的,则解压会在前台同步 IO 中完成。

总结:

  • 写入时的压缩发生在 Compaction 阶段,不会影响实时写入性能。

  • 读取时的解压可能发生在后台异步 IO 或前台同步 IO 中,具体取决于数据的访问模式和系统配置。

如果您需要进一步调整压缩策略,可以通过创建表时指定 COMPRESSION 属性来控制单个表的压缩算法(参考片段标题:表压缩)。例如:

CREATE TABLE my_table (
id INT PRIMARY KEY,
name VARCHAR(255)
) COMPRESSION = ‘zstd_1.0’;

以上内容基于以下文档信息:

  • 合并管理概述 → 合并的压缩算法

  • 压缩与编码

  • 表压缩

检索到的文档如下:

  1. log_transport_compress_all

  2. default_compress

  3. 合并管理概述

  4. 表压缩

  5. 压缩与编码

  6. default_compress_func

  7. 系统内存不足/泄漏

  8. 快速入门系列教程

  9. log_storage_compress_all

  10. 数据压缩概述