关于生成执行计划窥探问题

【TiDB 使用环境】Poc
【TiDB 版本】v8.5.4

使用TiDB时,我们最主要的是对Prepare语句缓存执行计划,但是语句发生硬解析时是通过窥探实际值来重新生成执行计划的,往往是晚上收集统计信息,晚上的业务行为和白天不同,因此可能会导致生成的执行计划是晚上传递的值,白天跑时候就可能跑偏,因此是否应该支持不窥探的形式来生成执行计划呢,这样做的好处是可以保证执行计划比较稳定。
其它数据库提供的能力如下:

  1. Oracle 支持硬解析首次窥探、不窥探,也支持自适应游标(一般配合开启窥探),也有随机失效执行计划设计避免解析风暴,一般采用不窥探或者窥探+自适应游标方案。(PS:开启窥探、不开启自适应游标会导致执行计划不稳定,这个在复杂业务场景下容易出问题,TiDB就类似于这种形式
  2. DB2 支持硬解析首次窥探,每次窥探,不窥探,一般采用不窥探保持执行计划稳定性。
  3. GaussDB 支持gplan(不窥探),cplan(每次都窥探),aplan(自适应窥探,类似于Oracle同时开启了窥探和自适应游标)。

我感觉TiDB可以加强下,优先支持下不窥探能力。同时也可以支持下explain select xx from t where id = ?这种执行计划的生成。

1 个赞

分析很深刻,完全切中了 TiDB 在高并发生产环境中执行计划不稳定(Plan Regression)的核心痛点。

如果直接use index呢?

这是一种无奈之举,目前的解决方法,对开发人员来说比较痛苦,开发更应该关注业务而不是怎么加hint,很多场景下也不好添加。

1 个赞

可以使用SQL Binding试试呢

我们更多的是SQL Binding ,不过这个情况多了,也很痛苦。

1 个赞

是啊,对于技术人员真的不是好事,无奈

1 个赞

Binding还不如hint,起码业务行为发生变化,研发可以感知。用了binding,时间久了可能都不知道这个binding是基于什么原因加上的。这个是作为应急的兜底方案,而且应该做成临时方案,应用加上hint后去掉binding。

对哦,SQL Binding一般要dba才有权限加

不窥探主要是TiDB 为了隐私保护 和 性能 / 易用性优化

我来内网问一问

好问题,binding一定是最后的兜底方案,不会经常使用的,也不利于SQL的健康。