单条SQL执行限制内存2G,同事写SQL查询没有limit 这条SQL执行占用18G的内存,为啥SET tidb_mem_quota_query = 2 << 30;没有生效

【 TiDB 使用环境】生产环境
【 TiDB 版本】
【复现路径】做过哪些操作出现的问题
【遇到的问题:问题现象及影响】
【资源配置】

【附件:截图/日志/监控】

tidb_mem_oom_action 值是什么?

你是在session级别控制的吧,得在同一个窗口用命令行执行set再执行sql

系统变量 tidb_mem_quota_query 单条SQL内存限制也是1G的

把这个参数关闭吧。

最后生效了吗

你这个场景:
1、默认tidb_distsql_scan_concurrency=15,极端情况下会缓存15个region。
2、decimal、tinyint等字段都存在内存放大问题,尤其decimal(40个字节)如果字段特别多的话可能会导致占用太多的内存。
3、tidb_enable_rate_limit_action=ON,该版本默认开启限流,会优先限流导致tidb缓存太多数据,没有及时触发cancel等oom-action动作。
4、假设你这个pushsubscribe是一个视图,里面存在union all等,那么会被放大,默认最多5倍(受tidb_executor_concurrency参数影响),即5 * 15个region。
5、如果前端开启了cursor fetch游标读等会导致读读较慢,tidb后侧数据积压较多,如果前端获取数据更快那么后端更不容易积压数据,因此采用官方建议的流式更佳。

优化方法,在session级别设置:
1、set tidb_distsql_scan_concurrency=2; 缓存更少的region数据,同时保持性能
2、set tidb_enable_rate_limit_action=OFF; 保证内存尽量不会超出tidb_mem_quota_query,减少tidb-server oom风险。
3、检查region,是否存在大region,尽量做splitRegion操作。
4、set tidb_enable_chunk_rpc=OFF;关闭 chunk_rpc减少内存放大问题。

更推荐升级到6.5版本,通过paging代替整个region的数据返回,减少了语句OOM的风险。
在6.5版本paging默认是开启的:

mysql> show variables like '%paging%';
+----------------------+-------+
| Variable_name        | Value |
+----------------------+-------+
| tidb_enable_paging   | ON    |
| tidb_max_paging_size | 50000 |
| tidb_min_paging_size | 128   |
+----------------------+-------+
3 rows in set (0.00 sec)
2 个赞

SET tidb_mem_quota_query = 2 << 30; statement 用于设置 TiDB 中单次 SQL 查询执行的内存配额。 此语句指定查询可以使用的最大内存量。

但需要注意的是,tidb_mem_quota_query 配置仅适用于设置该配置后执行的后续 SQL 语句。 它不会追溯限制以前执行的 SQL 语句的内存使用。

如果您的同事已经在没有内存限制的情况下执行了 SQL 查询,那么这些查询消耗的内存可能超过了指定的配额。 这些查询的内存使用不能追溯限制。

要对 SQL 查询执行内存限制,您需要确保在执行查询之前设置 tidb_mem_quota_query 配置。 此外,重要的是要考虑 TiDB 集群中的整体资源使用和分配,以防止内存消耗过多并优化性能。

如果要保证所有 SQL 查询都受内存限制,可以在 TiDB 配置文件(tidb.toml)中全局设置 tidb_mem_quota_query 配置。 通过这样做,内存限制将适用于在 TiDB 集群中执行的所有 SQL 查询。

修改配置文件后记得重启 TiDB 服务,新的设置才能生效。

如果您遇到任何问题或内存限制仍未按预期执行,建议您检查 TiDB 日志并咨询 TiDB 社区或支持渠道以获得进一步的帮助。

乍没看到最后的答案。。

这个全