问题现象
错误地触发了一类子查询合并改写:认为 condition_1 中 subqeury_1 是 subquery_2 的超集,则触发了子查询合并。
WHERE t1.c1 IN (SELECT t2.c1 FROM t2) AND t1.c1 NOT IN (SELECT t2.c1 FROM t2 WHERE t2.c2 != 'x');
--> 改写为
WHERE t1.c1 IN (SELECT t2.c1 FROM t2 WHERE LNNVL(t2.c2 != 'x'));
这个改写是不正确的:原因在于 NOT IN 中 WHERE t2.c2 != 'x' 对 t2.c1 并不具备过滤性。
关键诊断信息
触发条件
用户 SQL 的 WHERE 谓词中,使用 xxx IN subquery1 and xxx NOT IN subquery2,如果 subquery1 结果集是 subquery2 的超集,会触发。
事前巡检
检查 SQL 的问题写法。
事后诊断
正确性问题,只能通过对比结果集来发现。
问题原因
错误的改写策略。
问题的风险及影响
如果触发的话,将带了正确性危险,用户查询结果集可能不对。
影响租户
影响 OceanBase 数据库中的 SYS 租户和 Oracle 租户以及 MySQL 租户。
影响版本
OceanBase 数据库企业版 V2.2.77 GA(oceanbase-2.2.77-20210508211731)及之后版本、V3.1.2 GA(oceanbase-3.1.2-20210618150922)及之后版本、V3.2.3 GA(oceanbase-3.2.3.0-20220419)及之后版本、V3.2.4 GA(oceanbase-3.2.4.0-100000072022102819)及之后版本、V4.1.0 GA(oceanbase-4.1.0.0-100001122023040322)及之后版本、V4.2.1 GA(oceanbase-4.2.1.0-100000182023092722)及之后版本。
解决方法
升级至问题已修复版本。目前已修复的版本包括 OceanBase 数据库企业版 V2.2.77 BP19(oceanbase-2.2.77-119000122024060513)、V3.2.3 BP10 Hotfix8(oceanbase-3.2.3.3-110080012024022713)、V3.2.3 BP10 Hotfix9(oceanbase-3.2.3.3-110090012024041611)、V3.2.3 BP10 Hotfix10(oceanbase-3.2.3.3-110100012024042814)、V3.2.3 BP10 Hotfix11(oceanbase-3.2.3.3-110110032024052217)、V3.2.3 BP10 Hotfix12(oceanbase-3.2.3.3-110120012024060510)、V3.2.3 BP10 Hotfix13(oceanbase-3.2.3.3-110130012024061819)、V3.2.3 BP10 Hotfix14(oceanbase-3.2.3.3-110140012024082010)、V3.2.3 BP10 Hotfix15(oceanbase-3.2.3.3-110150012024102111)、V3.2.3 BP10 Hotfix16(oceanbase-3.2.3.3-110160012025021315)、V3.2.3 BP10 Hotfix17(oceanbase-3.2.3.3-110170012025032112)、V3.2.3 BP10 Hotfix18(oceanbase-3.2.3.3-110180012025060316)、V3.2.3 BP10 Hotfix19(oceanbase-3.2.3.3-110190022025082615)、V3.2.3 BP11(oceanbase-3.2.3.3-111000032024070822)、V3.2.4 BP8(oceanbase-3.2.4.8-108000142024041520)、V4.2.1 BP2(oceanbase-4.2.1.2-102010012023120119)。
禁用改写,使用
/*+NO_REWRITE*/Hint。
规避方式
暂无。