资讯 MySQL 9.7.2:LOAD DATA 残留 NULL 状态、POW(NULL) 返回 1 等会真踩到的修复

2026-10-10 21:06:02

MySQL 9.7.2:LOAD DATA 残留 NULL 状态、POW(NULL) 返回 1 等会真踩到的修复

MySQL 9.7.2(2026-07-28)里,下面这些行为修复会在生产查询或升级过程中直接表现为报错、错行或结果截断。

LOAD DATA 写入 NOT NULL 列后,同会话 INSERT 报 1263 / 1048

LOAD DATA 解析输入行时会把字段临时标记为可空。如果某一行给 NOT NULL 列提供了 NULL,LOAD DATA 在返回到同一线程之前,可能把字段的临时 NULL 状态留在表上。同一会话随后的 INSERT 会把合法非 NULL 值当成 NULL,返回 ER_BAD_NULL_ERROR:

ERROR 1263 (22004): Column set to default value; NULL supplied to NOT NULL column 'b' at row 1
ERROR 1048 (23000): Column 'b' cannot be null

(Bug #118060, #38939847)

POW() 传 NULL 指数返回 1

POW() 的指数为 NULL 时,错误地返回 1 而不是 NULL。(Bug #120779, #39641087)

NULL 传播被破坏后,POW(x, NULL) 参与的比较与聚合都会偏离预期。

IN 谓词含 DATE / TIME 常量时匹配到无关字符串

IN 谓词里包含 DATE 或 TIME 常量时,一个不在列表任何元素中的非时间字符串可能被判定为 true,把无关行带进结果集。(Bug #120787, #39649755)

AVG(ASCII(...)) 配合 SQL_BUFFER_RESULT 结果被截断

AVG() 作用于 ASCII() 等函数时,如果同时使用 SQL_BUFFER_RESULT,返回值可能被截断——小数精度计算没有为符号位预留空间。现在精度计算会考虑有符号值,255.0000 这类结果不再被截断。(Bug #120465, #39392429)

JSON 关系对偶视图更新改为先删后插

从嵌套子基表中删除行的 JSON 对偶视图更新,可能违反外键约束。更新处理现在先按反向绑定顺序执行删除,再执行插入和更新。(Bug #39566804)

从 8.x 升级数千对象时的内存持续增长

带着数千张表、视图、存储过程和事件从较早的 8.x 升级时,服务器内存占用会持续增长,造成明显的内存尖峰。该版本改进了内存管理。(Bug #117983, #37832455, #38031020)

hypergraph optimizer 的几处修复

  • SELECT DISTINCT ... LIMIT:基于物化的去重会先处理完所有 distinct 行再应用 limit;现在把限制传给去重环节,可以提前停止。由 SQL_BIG_RESULT 强制走的基于排序的 DISTINCT 行为不变。(Bug #36720017)
  • BETWEEN 常量边界:精确索引范围扫描之上会出现多余的 filter;现在识别为精确范围并移除该 filter。(Bug #37152269)
  • Hash join:低 LIMIT 查询可能产生不必要的落盘 I/O;优化器现在也会考虑内存 hash join。(Bug #36684053)
  • ORDER BY 中的非确定性表达式:使用带副作用的存储函数或 RAND() 这类非确定性函数时,每行可能被求值多次;现在排序前先物化行。(Bug #36578540)
  • ORDER BY + 低 LIMIT + 复合索引反向范围扫描:优化器过早移除排序时可能返回错误结果。(Bug #119198)
  • 索引列 IS NULL 过滤 + 同列 ORDER BY:可能做多余的 filesort;IS NULL 现在作为常量条件参与 order-by 简化。(Bug #119442)
  • 唯一索引上的 FORCE INDEX + IS NULL:仍会做 index dive,现在跳过。(Bug #117791)
  • GROUP BY ... WITH ROLLUP:常量表达式配合空的 USE INDEX FOR GROUP BY() hint 可能触发 assert;优化器现在识别常量分组不需要索引排序。(Bug #39505077)

线程池默认保留的空闲线程数从 2 增到 32

thread_pool_max_unused_threads 的默认值由 2 改为 32。(Bug #39405207)

其他需要注意的行为变更

  • INSERT() 处理多字节字符时,位置超出输入字符串仍会插入字符。(Bug #113962)
  • TIMESTAMPDIFF() 在带 WHERE 子句时返回意外结果。(Bug #108143)
  • JSON_VALUE() 使用 RETURNING DATETIME 和 DEFAULT 时,在 DATE 上下文中可能返回无效的常量日期。(Bug #120788)
  • 关键字定义修正:CUBE、EXTERNAL、QUALIFY、TABLESAMPLE 为保留字;MANUAL、PARALLEL 为非保留字。(Bug #114874)
  • 复制:SOURCE_RETRY_COUNT=0 在各重连路径上统一视为无限重试;此前在后续出现瞬时连接丢失时可能停止重试。(Bug #39086875)
  • 打包:不再支持 Enterprise Linux 7。
  • 计划移除的弃用复制系统变量:group_replication_communication_stack、group_replication_ip_allowlist。(WL #17300)

升级时注意

  • 遇到 1263 / 1048 时,确认是否由 LOAD DATA 后残留的临时 NULL 状态引起;临时规避是出现该报错后重新建立会话,正式修复在 9.7.2。
  • 对象数量达数千的 8.x 实例,升级前先确认目标版本已包含上述内存修复。
  • 依赖 POW(x, NULL) = 1、或依赖 IN 谓词对非时间字符串旧匹配行为的查询,需要复核结果。
  • 把 CUBE、EXTERNAL、QUALIFY、TABLESAMPLE 当标识符使用的语句要加反引号。
  • 复制拓扑中使用 SOURCE_RETRY_COUNT=0 的实例,重试语义已统一为无限重试。
  • Enterprise Linux 7 已不再支持,升级前先迁移运行平台;两个 group_replication_* 变量在移除前完成替换。
复制全文 生成海报 MySQL 运维 数据库

推荐文章

程序员茄子在线接单