实验二十八 SQL PATCH调优

1.使用测试用户tester连接实验GaussDB实例。

sql 复制代码
gsql -d testdb -h 192.168.3.60 -U tester -p 8000 -W Gauss@123 -r

2.创建测试表及索引。

sql 复制代码
create table hint_t1(a int, b int, c int);
create index on hint_t1(a);

3.插入测试数据。

sql 复制代码
insert into hint_t1 select generate_series(1,100000),generate_series(1, 100000),generate_series(1, 100000);

4.执行如下命令收集hint_t1表统计信息。

sql 复制代码
analyze hint_t1;

5.执行SQL语句。

sql 复制代码
testdb=> explain analyze select /*+ rows(hint_t1 -90000)*/ a from hint_t1 where hint_t1.a>999;
 id |        operation        | A-time | A-rows | E-rows | Peak Memory | A-width | E-width |     E-costs      
----+-------------------------+--------+--------+--------+-------------+---------+---------+------------------
  1 | ->  Seq Scan on hint_t1 | 52.324 |  99001 |   9026 | 63KB        |         |       4 | 16.339..1631.000
(1 row)

 Predicate Information (identified by plan id) 
-----------------------------------------------
   1 --Seq Scan on hint_t1
         Filter: (a > 999)
         Rows Removed by Filter: 999
(3 rows)

       ====== Query Summary =====       
----------------------------------------
 Datanode executor start time: 0.044 ms
 Datanode executor run time: 65.920 ms
 Datanode executor end time: 0.027 ms
 Planner runtime: 0.545 ms
 Query Id: 1948932738745690863
 Total runtime: 66.005 ms
(6 rows)

从上述执行计划可以看到,查询时使用的是Seq scan全表扫描,耗时比较长。因为hint_t1表存在a列的索引,可以考虑使用IndexOnlyScan的方式进行优化。

6.执行SQL查询语句。

sql 复制代码
select a from hint_t1 where hint_t1.a>999;

7.使用管理员用户root连接实验GaussDB实例。

sql 复制代码
gsql -d testdb  -p 8000 -r

8.查询视图dbe_perf.summary_statement获取unique_sql_id。

sql 复制代码
testdb=# select unique_sql_id,query from dbe_perf.summary_statement where query like 'select%hint_t1%';
 unique_sql_id |                  query                   
---------------+------------------------------------------
    3752218171 | select a from hint_t1 where hint_t1.a>?;
(1 row)

9.创建调优SQL PATCH,使该SQL语句走IndexOnlyScan。

sql 复制代码
testdb=# select * from dbe_sql_util.create_hint_sql_patch('patch1',3752218171,'IndexOnlyScan(hint_t1)');
 create_hint_sql_patch 
-----------------------
 t
(1 row)

其中unique_sql_id使用之前步骤查询到的id。

10.使用测试用户tester连接实验GaussDB实例。

sql 复制代码
gsql -d testdb -h 192.168.3.60 -U tester -p 8000 -W Gauss@123 -r

11.再次执行语句,查看执行计划。

sql 复制代码
[Ruby@gs01 ~]$ gsql -d testdb -h 192.168.3.60 -U tester -p 8000 -W Gauss@123 -r
gsql ((GaussDB Kernel 505.2.1.SPC0800 build 85996fbb) compiled at 2025-07-03 01:15:58 commit 10558 last mr 24271 release)
SSL connection (cipher: ECDHE-RSA-AES128-GCM-SHA256, bits: 128)
Type "help" for help.

testdb=> explain analyze select /*+ rows(hint_t1 -90000)*/ a from hint_t1 where hint_t1.a>999;
NOTICE:  Plan influenced by SQL hint patch
 id |                     operation                      | A-time | A-rows | E-rows | Peak Memory | A-width | E-width |     E-costs     
----+----------------------------------------------------+--------+--------+--------+-------------+---------+---------+-----------------
  1 | ->  Index Only Scan using hint_t1_a_idx on hint_t1 | 32.733 |  99001 |  99026 | 93KB        |         |       4 | 0.000..2155.605
(1 row)

    Predicate Information (identified by plan id)     
------------------------------------------------------
   1 --Index Only Scan using hint_t1_a_idx on hint_t1
         Index Cond: (a > 999)
(2 rows)

       ====== Query Summary =====       
----------------------------------------
 Datanode executor start time: 0.037 ms
 Datanode executor run time: 44.278 ms
 Datanode executor end time: 0.019 ms
 Planner runtime: 0.545 ms
 Query Id: 1948932738745700674
 Total runtime: 44.374 ms
(6 rows)

 ====== Query Others ===== 
---------------------------
 Bypass: Yes
(1 row)

可以看到已经使用了SQL PATCH,扫描时使用的Index Only Scan,执行时间从66ms降到了44ms。

在实际业务场景中,如果客户应用侧不方便修改SQL代码,可以考虑使用SQL PATCH的方式来改变SQL语句的执行计划。

12.执行如下命令删除测试表。

sql 复制代码
drop table hint_t1;

13.使用管理员用户root连接实验GaussDB实例。

sql 复制代码
gsql -d testdb  -p 8000 -r

14.执行如下命令删除SQL PATCH。

sql 复制代码
[Ruby@gs01 ~]$ gsql -d testdb  -p 8000 -r
gsql ((GaussDB Kernel 505.2.1.SPC0800 build 85996fbb) compiled at 2025-07-03 01:15:58 commit 10558 last mr 24271 release)
Non-SSL connection (SSL connection is recommended when requiring high-security)
Type "help" for help.

testdb=# select * from dbe_sql_util.drop_sql_patch('patch1');
 drop_sql_patch 
----------------
 t
(1 row)
相关推荐
AIgorithmGEEK2 小时前
MySQL 索引全解(下):建、查、删实战与知识速查表
数据库·mysql·b+树·索引
唠点键盘之外的5 小时前
26 向量数据库实战:从 0 搭一条能用的检索链路(pgvector + Spring AI)
数据库·人工智能·spring
云和恩墨5 小时前
数据库监控简史:监控不止于告警——从图表大爆发到健康管理闭环
数据库
ly76895 小时前
MongoDB 事务开销实测:快照隔离下的写冲突、重试与分片事务边界
数据库·mongodb·事务·分片集群·快照隔离·写冲突
豆角焖肉5 小时前
Spring AOP 自定义注解实现系统操作日志
数据库·自定义注解·springaop·操作日志·aop 切面
金伟API10246 小时前
不会写复杂SQL怎么办?
数据库·sql
执笔为剑7 小时前
2.1.2-1、V8R3迁移到V8R6-Oracle兼容特性
数据库
geovindu7 小时前
sql:Search-Optimized SQL Queries using mysql 9.0
android·数据库·sql·mysql·数据库开发·数据库架构
for_ever_love__7 小时前
MySQL SELECT 与 WHERE 优化实战:可搜索条件、联合索引与执行计划
数据库·mysql·oracle·select·where·条件优化·查询优化技巧
2501_931803757 小时前
MySQL 锁机制详解
数据库·mysql