DML无锁数据变更可以将单个SQL拆分成多个批次执行,能更好地满足业务方对大量数据变更的需求,例如历史数据清理、全表更新字段等,保证执行效率,减小对数据库性能、数据库空间等的影响。

背景信息

当业务累积了大量数据时,需要定期清除表中的数据,或对在线数据和历史数据进行分隔管理。您可能会遇到以下问题:
  • 单条SQL影响行数过多,日志超过阈值导致任务执行失败。
  • SQL没有使用索引导致锁表,数据库负载增加,甚至造成业务故障。
此类问题通常可通过分批执行的方法解决,但是仍存在风险,例如:
  • 研发写程序分批处理:
    • 分批方式不当,例如直接用LIMIT进行分批,可能仍会锁表。
    • 分批执行的频率没有控制好,会造成主备延迟过大。
  • DBA提取目标数据手动拆分:

    人工拆分非常繁琐,工作量大,且易出错,并且很难进行动态调整。

为解决上述问题,DMS提供了DML无锁变更。具体操作,请参见DML无锁变更

支持的数据库类型

  • MySQL:RDS MySQLPolarDB MySQL版MyBase MySQLPolarDB分布式版、其他来源MySQL
  • PostgreSQL:RDS PostgreSQLPolarDB PostgreSQL版MyBase PostgreSQL、其他来源PostgreSQL
  • MariaDB:RDS MariaDB、其他来源MariaDB
  • OceanBase MySQL模式
  • PolarDB PostgreSQL版(兼容Oracle)

功能特点

  • 不会影响业务。
  • 减小数据变更对数据库性能、数据库空间等的影响。
  • 能更好地满足业务方对大量数据变更的需求,保证数据变更的执行效率。

主要原理

  • 分批执行单个SQL:强大的DMS引擎将单个SQL拆分成多个批次执行。
  • 每个批次执行后有Sleep(暂停)进行缓冲。

使用限制

当前仅支持UPDATE、DELETE、INSERT_SELECT类型的SQL。

SQL类型限制项
UPDATE、DELETE
  • 仅支持UPDATE或DELETE单表操作。
  • 更新、删除(UPDATE、DELETE)数据时必须添加WHERE子句。若需要更新或删除全表,则需要添加WHERE 1=1子句。
  • 不支持UPDATE、DELETE包含子查询筛选条件。
  • 不支持LIMIT子句。
INSERT_SELECT
  • SELECT子句仅支持单表操作。
  • SELECT部分需要带上WHERE子句,若需要SELECT全表数据,则需要带上WHERE 1=1
  • SELECT部分不支持LIMIT、ORDER BY、GROUP BY等子句。

适用场景

  • 历史数据清理。
  • 全表更新字段。