• [集群&DWS] GaussDB(DWS)资源监控系列一:作业级别的监控(TopSQL)
    【摘要】 实时TopSQL,历史TopSQL。总体介绍GaussDB(DWS)资源监控的作业级别监控,分为实时级别监控(实时TopSQL)与历史级别监控(历史TopSQL)。实时TopSQL可以完成对于运行中的SQL进行资源监控,其可以通过查询gs_wlm_sesssion_statistics查询得到。历史TopSQL可以对运行结束之后的SQL进行监控其可以通过查询gs_wlm_session_history得到相应的资源消耗信息。如图1所示,在设置enable_resource_track为on,resource_track_level为query的时候,当该SQL的执行代价大于设定的resource_track_cost的时候,就可以在实时TopSQL中查到相应的SQL执行信息,当该SQL执行结束之后对于其执行时间大于resource_track_duration的SQL即可以在历史TopSQL中查询到。在设置enable_resource_record为on的时候,每过三分钟会将gs_wlm_session_history中的数据落盘存到gs_wlm_session_info中。对于存入到gs_wlm_session_info中的数据可以通过设定topsql_rentention_time对其中的数据进行老化处理。图1TopSQL功能总体关系图实时TopSQL系统提供了query级别和算子级别的资源监控实时视图用来查询实时TopSQL。资源监控实时视图记录了查询作业运行时的资源使用情况(包括内存、下盘、CPU时间和IO等)以及性能告警信息,这里相关的视图如图3.1所示。图2实时TopSQL相关的视图对于实时TopSQL而言,其中的资源数据的更新在这个SQL执行的过程中每10s会更新收集一次。历史TopSQL系统提供了query级别和算子级别的资源监控历史视图来查询历史TopSQL。资源监控历史视图记录了查询作业运行结束时的资源使用情况(包括内存、下盘、CPU时间、IO等)和运行状态信息(包括报错、终止、异常等)以及性能告警信息。但对于由于FATAL、PANIC错误导致查询异常结束时,状态信息列只显示aborted,无法记录详细的异常信息。这里需要开启参考手册开启相应的GUC参数。这里相关的视图与表如图4.1所示。图3历史TopSQL相关的视图与表这里以query当前CN查询为例说一下这个整体的流程,当作业执行完之后就会从实时static那个视图里存储到gs_wlm_session_history这个视图当中,默认三分钟之后数据就会转存到gs_wlm_session_info这个表中,存到数据库当中。在这里需要注意的是gs_wlm_session_history是一个视图,而gs_wlm_session_info是一个实际的表。另外在配置相关的GUC时,要注意有可能会配置的hash表大小过小导致数据存储不下的情况。对于TopSQL能够支持记录的规格请详见对应版本手册中的描述。原文链接:https://bbs.huaweicloud.com/blogs/215673【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [集群&DWS] GaussDB(DWS)云端运维系列第六期:参数调整(参数组,单集群参数调整)
    为了方便您配置数据库参数,GaussDB(DWS) 提供了参数模板的功能,参数模板中包含了一些常用的数据库参数。您可以直接在GaussDB(DWS) 管理控制台上管理参数模板,将参数模板应用到集群后,可以直接在集群的“参数修改”页面中修改参数。一、参数模板概述     参数模板是一组适用于数据仓库的参数,模板中的参数都设置了默认值,这些参数包括会话超时时间、日期和时间格式等。通过调整参数值,可以使数据库更好地适配实际业务。在创建集群时,您可以为集群指定一个参数模板,模板中的参数将被应用于该GaussDB(DWS) 集群中的所有数据库,如果您未指定参数模板,系统将为集群应用默认的参数模板。当集群创建成功后,您可以在集群“参数修改”页面修改参数,也可以在参数模板管理页面,选择其他参数模板或者创建新的参数模板重新应用到对应的集群。     GaussDB(DWS) 为每个版本的数据仓库预置了一个默认参数模板,默认参数模板不支持删除和修改。如果用户想要修改参数模板中的参数值,可以创建一个自定义参数模板,自定义参数模板中的参数值允许被修改。自定义参数模板被应用到集群后,它与集群并无关联关系,之后,如果您修改了该自定义模板中的参数值,其修改并不会同步到集群,您需要重新将该参数模板应用到集群,才能使修改后的参数值应用到集群。同样的,如果您在集群详情页面修改参数,其修改也不会同步到参数模板。参数说明     参数配置如图所示:      其中,各个参数的具体含义及配置方法如下表所示:    参数名称参数描述默认值session_timeoutSession闲置超时时间,单位为秒,0表示关闭超时限制。取值范围:0 ~ 86400。600datestyle设置日期和时间值的显示格式。ISO,MDYfailed_login_attempts输入密码错误的次数达到该参数所设置的值时,帐户将会被自动锁定。配置为0时表示不限制密码输入错误的次数。取值范围:0 ~ 1000。10timezone设置显示和解释时间类型数值时使用的时区。UTClog_timezone设置服务器写日志文件时使用的时区。UTCenable_resource_record设置是否开启资源记录功能。当SQL语句实际执行时间大于resource_track_duration参数值(默认为60s,可自行设置)时,监控信息将会归档。此功能开启后会引起存储空间膨胀及轻微性能影响,不用时请关闭。说明:归档:监控信息保存在history视图,归档在info表。归档时间为三分钟,归档后history视图中的记录会被清除。history视图GS_WLM_SESSION_HISTORY,对应存入info表GS_WLM_SESSION_INFO。history视图GS_WLM_OPERATOR_HISTORY,对应存入info表GS_WLM_OPERATOR_INFO。offresource_track_cost设置对语句进行资源监控的最小执行代价。值为-1或者执行语句代价小于10时,不进行资源监控。值大于等于0时,执行语句的代价大于等于10并且超过这个参数的设定值就会进行资源监控。SQL语句的预估执行代价可通过执行SQL命令Explain进行查询。此参数在集群版本1.5.0或以上有效。100000resource_track_duration设置当前会话资源监控实时视图中记录的语句执行结束后进行归档的最小执行时间。值为0时,资源监控实时视图中记录的所有语句都会进行历史信息归档。值大于0时,资源监控实时视图中记录的语句的执行时间超过设定值就会进行历史信息归档。60password_effect_time设置帐户密码的有效时间,临近或超过有效期系统会提示用户修改密码。取值范围为0 ~999,单位为天。设置为0表示不开启有效期限制功能。此参数在集群版本1.5.0或以上有效。90update_lockwait_timeout该参数控制并发更新同一行时单个锁的最长等待时间。当申请的锁等待时间超过设定值时,系统会报错。0表示不等待,有锁时直接报错。默认值120000,单位为毫秒。此参数在集群版本1.5.0或以上有效。120000二、创建参数模板  如果默认参数模板中的参数值无法满足业务,用户可以创建自定义参数模板,并修改其中的参数值,从而更好地适配业务。  创建参数模板操作步骤如下:登录GaussDB(DWS) 管理控制台。在左侧导航栏中,单击“参数模板管理”。单击“创建参数模板”,然后设置以下参数。· “数据库引擎”:选择一个数据库引擎。· “数据库版本”:选择一个数据库版本。· “参数模板名”:填写新参数模板的名称。   参数模板名称长度为4~64个字符,必须以字母开头,不区分大小写,可以包含字母、数字、中划线或者下划线,不能包含其他的特殊字符。· “描述”:填写新参数模板的描述信息。此参数为可选参数。三、应用参数模板到集群  集群创建成功后,用户可以为集群应用一个新的参数模板,将参数模板中所有参数的值应用到对应的集群中。  应用参数模板的操作步骤如下:登录GaussDB(DWS) 管理控制台。在左侧导航栏中,单击“参数模板管理”。选择一个目标参数模板,在“操作”列中单击“应用”。在“参数模板应用”对话框,选择目标集群。单击“确定”。     如果重新应用的参数模板与集群原来的参数取值不同,系统会弹窗显示两组参数值的对比。四、删除参数模板  对于多余或者不再使用的参数模板,用户可以将其删除,但是不支持删除默认参数模板。成功删除的参数模板无法恢复,请用户谨慎操作。登录GaussDB(DWS) 管理控制台。在左侧导航栏中,单击“参数模板管理”。在待删除的参数模板右侧操作列,单击“删除”。在弹出的对话框,单击“是”。原文链接:https://bbs.huaweicloud.com/blogs/212712【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [存储] GaussDB(DWS) SQL On Anywhere之外表
    背景Hadoop的诞生是划时代的数据变革,但关系型数据库时代的存留也为Hadoop真正占领数据库领域埋下了许多的障碍。对SQL(尤其是PL/SQL)的支持一直是Hadoop大数据平台在替代旧数据时代亟待解决的问题。Hadoop对SQL数据库的支持度一直是企业用户最关心的诉求点之一,也是他们选择的Hadoop平台的重要标准。Hadoop开源技术具有高扩展性,实际生产环境已经可以支持部署几千个 物理节点,提供PB级数据分析能力,支持运行在通用廉价的x86 Linux服 务器上,数据存储在内置盘上,且无商业软件license费用;Hadoop通过技术能力(sql支持,MR内存计算,MPP)的演进以及众多 非传统关系型数据库厂商的支持,正在从最初的只处理低价值低密度数 据的批处理型任务,向中等价值数据的分析处理任务演进。融合大数据生态与MPPDB传统数据库的融合方案有以下两种:(1)远程查询方案,以关系型数据库作为集成节点,将查询发送给Hadoop,并接收Hadoop的计算结果,查询分析在Hadoop平台完成,采用这种方式的厂商有 Oracle,Teradata,SQL Server等;(2)查询引擎直接访问HDFS数据方案,分析由传统数据库引擎完成,代表产品有PIVOTAL HAWQ,IBM BigSQL 3.0等。出于性能考虑GaussDB(DWS)选择的是第二种方案。CN将任务分解下发至各个DN,以实现节点间并行,使得调度计算节点更靠近数据存储节点。特点支持多DN并发查询;支持和本地多表join;支持analyze收集统计信息;格式支持丰富,易扩展。使用用户通过建立外部服务器Server(外部服务器是存储HDFS集群信息、OBS服务器信息或其他同构集群信息的载体)-- 创建HDFS_Server。CREATE hdfs_server FOREIGN DATA WRAPPER HDFS_FDW OPTIONS (     address '10.10.0.100:25000,10.10.0.101:25000',     hdfscfgpath '/opt/hadoop_client/HDFS/hadoop/etc/hadoop',     type'HDFS');创建Foreign Table在GaussDB(DWS)数据库内部定义对应的HDFS/OBS数据源上结构化数据表的结构。-- 建立不包含分区列的HDFS外表,表关联的HDFS server为hdfs_server,表region对应的HDFS服务器上的文件格式为‘orc’,在HDFS文件系统上对应的文件目录为'/user/hive/warehouse/mppdb.db/region_orc11_64stripe/'。CREATE FOREIGN TABLE region(     R_REGIONKEY INT4,     R_NAME TEXT,     R_COMMENT TEXT)SERVER    hdfs_serverOPTIONS(     FORMAT 'orc',     encoding 'utf8',     FOLDERNAME '/user/hive/warehouse/mppdb.db/region_orc11_64stripe/')DISTRIBUTE BY roundrobin;查看外表-- 查看外表。SELECT * FROM pg_foreign_table WHERE ftrelid='region'::regclass;  ftrelid | ftserver | ftwriteonly |                                  ftoptions---------+----------+-------------+------------------------------------------------------------------------------   16510 |    16509 | f           | {format=orc,foldername=/user/hive/warehouse/mppdb.db/region_orc11_64stripe/}(1 row)本章简单介绍了GaussDB(DWS)通过外表访问HDFS/OBS上的文件,下一篇中将介绍SQL On Hadoop系统分类,以及业内主流的SQL On Hadoop系统,如HIve、Impala、HAWQ等。原文链接:https://bbs.huaweicloud.com/blogs/209157【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [技术干货] SQLite表达式详解(分享)
    一、常用表达式:    和大多数关系型数据库一样,SQLite能够很好的支持SQL标准中提供的表达式,其函数也与SQL标准保持一致,如:    ||    *    /    %    +    -    <<   >>   &    |    <    <=   >    >=    =    ==   !=   <>   IS   IS NOT   IN   LIKE     AND       OR    ~    NOT在上面的表达式中,唯一需要说明的是"||",该表达式主要用于两个字符串之间的连接,其返回值为连接后的字符串,即便该操作符两边的操作数为非字符串类型,在执行该表达式之前都需要被提前转换为字符串类型,之后再进行连接。二、条件表达式:    该表达式的语法规则如下:    1). CASE x WHEN w1 THEN r1 WHEN w2 THEN r2 ELSE r3 END    2). CASE WHEN x=w1 THEN r1 WHEN x=w2 THEN r2 ELSE r3 END  对于第一种情况,条件表达式x只需计算一次,然后分别和WHEN关键字后的条件逐一进行比较,直到找到相等的条件,其比较规则等价于等号(=)表达式。如果找到匹配的条件,则返回其后THEN关键字所指向的值,如果没有找到任何匹配,则返回ELSE关键字之后的值,如果不存在ELSE分支,则返回NULL。对于第二种情况,和第一种情况相比,唯一的差别就是表达式x可能被多次执行,比如第一个WHEN条件不匹配,则继续计算后面的WHEN条件,其它规则均与第一种完全相同。最后需要说明的是,以上两种形式的CASE表达式均遵守短路原则,即第一个表达式的条件一旦匹配,其后所有的WHEN表达式均不会再被执行或比较。三、转换表达式:    该表达式的语法规则如下:    CAST(expr AS target_type)该表达式会将参数expr转换为target_type类型,具体的转换规则见如下列表:目标类型转换规则描述TEXT如果转换INTEGER或REAL类型的值到TEXT类型直接转换即可,就像C/C++接口函数sqlite3_snprintf所完成的工作。REAL如果转换TEXT类型的值到REAL类型,在该文本的最前部,将可以转换为实数的文本转换为相应的实数,其余部分忽略。其中该文本值的前导零亦将被全部忽略。如果该文本值没有任何字符可以转换为实数,CAST表达式的转换结果为0.0。INTEGER如果转换TEXT类型的值到INTEGER类型,在该文本的最前部,将可以转换为整数的文本转换为相应的整数,其余部分忽略。其中该文本值的前导零亦将被全部忽略。如果该文本值没有任何字符可以转换为整数,CAST表达式的转换结果为0。如果转换将一个实数值转换为INTEGER类型,则直接截断实数小数部分。如果实数过大,则返回最大的负整数:-9223372036854775808。NUMERIC如果转换文本值到NUMERIC类型,则先将该值强制转换为REAL类型,只有在将REAL转换为INTEGER不会导致数据信息丢失以及完全可逆的情况下,SQLite才会进一步将其转换为INTEGER类型。 最后需要说明的是,如果expr为NULL,则转换的结果也为NULL。
  • [问题求助] 【fi 华为flink sql】【XXX功能】flink sql 是怎么读和写Gauss高斯数据库的?
    【功能模块】【fi  华为flink  sql】【XXX功能】flink sql 是怎么读和写Gauss高斯数据库的?【操作步骤&问题现象】1、我想迁移这部分功能到开源的flink 1.12上, 使得  开源的flink  sql也支持  读和写 Gauss高斯数据库 ?2、【截图信息】【日志信息】(可选,上传日志内容或者附件)
  • [开发应用] 【GaussDB A 8.1.0】【SQL占用cpu】统计sql占用的cpu
    【功能模块】【操作步骤&问题现象】客户要统计vacuum full对cpu的占用,我在pgxc_wlm_session_info中找不到vacuum full对应的记录,是怎么回事,需要什么设置么?【截图信息】【日志信息】(可选,上传日志内容或者附件)
  • [技术干货] SQL update select结合分享
    QL update select语句最常用的update语法是:UPDATE TABLE_NAMESET column_name1 = VALUE WHRER column_name2 = VALUE如果我的更新值Value是从一条select语句拿出来,而且有很多列的话,用这种语法就很麻烦第一,要select出来放在临时变量上,有很多个很难保存。 第二,再将变量进行赋值。列多起来非常麻烦,能不能像Insert那样,把整个Select语句的结果进行插入呢? 就好象下面::INSERT INTO table1(c1, c2, c3)(SELECT v1, v2, v3 FROM table2)答案是可以的,具体的语法如下:UPDATE table1 aliasSET (column_name,column_name ) = (SELECT (column_name, column_name)FROM table2WHERE column_name = alias.column_name)WHERE column_name = VALUE下面是这样一个例子: 两个表a、b,想使b中的memo字段值等于a表中对应id的name值 表a:id  name 1   王 2   李 3   张表b:    id ClientName 1 2 3(MS SQL Server)语句:UPDATE b  SET  ClientName  = a.name  FROM a,b  WHERE a.id = b.id(Oralce)语句:UPDATE b  SET  (ClientName)  =  (SELECT name FROM a WHERE b.id = a.id)update set from 语句格式 当where和set都需要关联一个表进行查询时,整个update执行时,就需要对被关联的表进行两次扫描,显然效率比较低。对于这种情况,Sybase和SQL SERVER的解决办法是使用UPDATE…SET…FROM…WHERE…的语法,实际上就是从源表获取更新数据。在 SQL 中,表连接(left join、right join、inner join 等)常常用于 select 语句。 其实在 SQL 语法中,这些连接也是可以用于 update 和 delete 语句的,在这些语句中使用 join 还常常得到事半功倍的效果。UPDATE T_OrderForm SET T_OrderForm.SellerID =B.L_TUserIDFROM T_OrderForm A LEFT JOIN T_ProductInfo  B ON B.L_ID=A.ProductID用来同步两个表的数据!Oralce和DB2都支持的语法:UPDATE A SET (A1, A2, A3) = (SELECT B1, B2, B3 FROM B WHERE A.ID = B.ID)MS SQL Server不支持这样的语法,相对应的写法为:UPDATE A SET A1 = B1, A2 = B2, A3 = B3 FROM A LEFT JOIN B ON A.ID = B.ID个人感觉MS SQL Server的Update语法功能更为强大。MS SQL SERVER的写法:UPDATE A SET A1 = B1, A2 = B2, A3 = B3 FROM A, B WHERE A.ID = B.ID在Oracle和DB2中的写法就比较麻烦了,如下:UPDATE A SET (A1, A2, A3) = (SELECT B1, B2, B3 FROM B WHERE A.ID = B.ID)WHERE ID IN (SELECT B.ID FROM B WHERE A.ID = B.ID)
  • [集群&DWS] GaussDB(DWS) 数据库安全设置之三权分立
    【摘要】 为了保护集群数据的安全,GaussDB(DWS)支持对集群设置三权分立(系统管理员、安全管理员、审计管理员),使用不同类型的用户分别控制不同权限的模式。GaussDB(DWS)创建集群时默认用户是SYSADMIN属性的系统管理员,具备系统最高权限。在实际业务管理中,为了避免系统管理员拥有过度集中的权利带来高风险,可以设置三权分立,将系统管理员的权限分立给安全管理员和审计管理员。三权分立后,系统管理员将不再具有CREATEROLE属性(安全管理员)和AUDITADMIN属性(审计管理员)能力。即不再拥有创建角色和用户的权限,并不再拥有查看和维护数据库审计日志的权限。关于CREATEROLE属性和AUDITADMIN属性的更多信息请参考 CREATE ROLE。默认的用户权限对象名称系统管理员安全管理员审计管理员普通用户表空间对表空间有创建、修改、删除、访问、分配操作的权限。不具有对表空间进行创建、修改、删除、分配的权限,访问需要被赋权。表对所有表有所有的权限。仅对自己的表有所有的权限,对其他用户的表无权限。索引可以在所有的表上建立索引。仅可以在自己的表上建立索引。模式对所有模式有所有的权限。仅对自己的模式有所有的权限,对其他用户的模式无权限。函数对所有的函数有所有的权限。仅对自己的函数有所有的权限,对其他用户放在public这个公共模式下的函数有调用的权限,对其他用户放在其他模式下的函数无权限。自定义视图对所有的视图有所有的权限。仅对自己的视图有所有的权限,对其他用户的视图无权限。系统表和系统视图可以查看所有系统表和视图。只可以查看部分系统表和视图。详细请参见系统表和系统视图。三权分立的权限最小化设置将数据库安全提升一个档次。如何实现三权分立的设置,请看如下:1、在数据仓库服务界面创建集群后,单击集群名称,进入集群详情,在详情页签中点击“安全设置”。2、进入“安全设置”,呈现设置界面。3、打开“三权分立”开关,可进行设置安全管理员及审计管理员用户名及密码(默认系统管理员在创建集群时已设定)。4、设置完成后,对于审计配置建议进行设置,审计也是数据库运行过程的关键日志。   审计保留策略建议“时间优先”,最长可保留730天,再根据实际需要将越权访问、DML、DDL等分别设置,数据仓库服务还提供的审计日志转储OBS的功能,设置转储的OBS桶及路径,在转储周期内将生成审计日志文件,直接放在您的OBS桶中,方便查看。5、设置完后,点击应用,成功后即可连接数据库查看三权分立的效果。审计查询命令是数据库提供的sql函数pg_query_audit,其原型为:pg_query_audit(timestamptz startime,timestamptz endtime,audit_log)参数startime和endtime分别表示审计记录的开始时间和结束时间,audit_log表示所查看的审计日志信息所在的物理文件路径,当不指定audit_log时,默认查看连接当前实例的审计日志信息。通过sql函数pgxc_query_audit可以查询所有CN节点的审计日志,其原型为:pgxc_query_audit(timestamptz startime,timestamptz endtime)说明: startime和endtime的差值代表要查询的时间段,其有效值为从startime日期中的00:00:00开始到endtime日期中的23:59:59之间的任何值。请正确指定这两个参数,否则将查不到需要的审计信息。原文链接:https://bbs.huaweicloud.com/blogs/180975【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [集群&DWS] GaussDB(DWS)负载管理核心技术解密二: 白话历史资源监视
    文章目录1. 负载管理简介2. 资源监视功能介绍负载管理(WLM)简介对于任何一个分布式数据库而言,无论数据库集群规模有多大,其计算资源(CPU、内存)与存储资源(磁盘空间、网络、IO)总归是有上限的。对于数据仓库应用而言,随着业务规模的逐日累积,当数据量或者查询作业达到一定的规模,不同组织、不同用户之前的必然会出现计算、存储资源的争抢,在无人干预的情况下,数据库系统通常会“笨”的想着把你的所有业务都尽可能快的执行完,通常会导致所有的业务执行速度都变慢了。GaussDB 负载管理(WLM)存在的目的就是为了让资源的分配合理化,重要的作业优先运行,次要的作业在资源不足情况下避免争抢他人资源。当然,如何能用好GaussDB 负载管理(WLM)的配置功能,不是一件一蹴而就的事情,业务是复杂的,一个组织/用户的运行作业是计算密集型还是存储密集型,往往通过猜得到的结果是背道而驰的。这也是本文存在的意义,希望读者能够通过GaussDB所提供的资源监视功能,将资源监视功能作为有效的度量工具,来衡量各组织/用户的资源争抢情况,进而通过负载管理功能做好计算/存储资源的划分,让你的数据库“聪明”起来。资源监视功能介绍对于用户而言,数据库负载不高的情况下,通常不会在意数据库里面跑了什么作业,通常当用户察觉到作业变慢的时候,才会开始琢磨作业为什么慢了,是不是数据库里面有别的作业影响到我了。此时,用户将会找到管理员,要求解决性能劣化的问题。而用户给管理员提供的信息会非常简单,在什么时间执行了一个什么语句,以前这个语句几分钟能够运行结束,现在要多长时间才能跑完。并且,劣化作业有可能因业务原因,不能随意执行,无法让管理员去复现定位。管理员只能等到数据库系统中,依据这简单的信息,期望能发现一些线索。GaussDB提供了完善的资源监视功能,能够帮助管理员在这两个信息的基础上分析历史某个时间点发生的问题。总结一下,管理员现在拿到的信息:1) 作业执行起始时间;2) 用户名; 3) 作业的SQL语句。下面,请跟随我以管理员的视角,在有限信息的情况下,来逐层递进分析,找到作业“慢”在哪。功能一:历史TopSQLGaussDB 提供了记录所有在数据库中执行SQL语句的功能,管理员可以通过打开enable_resource_track开关来启用这个功能,并且可以调整resource_track_duration参数来过滤掉执行时间较短的作业,着重于分析执行时长较长的作业。GaussDB 提供记录历史TopSQL这一功能的目的,就是为了方便用户做性能调优,TopSQL的数据表pgxc_wlm_session_history中详细记录了作业的执行时间、内存消耗、下盘量、CPU消耗、IO占用等信息,在业务变更、作业变更前后,可通过对比来分析SQL是否出现劣化。数据表pgxc_wlm_session_history提供的关键信息简述如表格,管理员能够分析的可能现象也在表格中:字段名称字段描述分析出可能的现象block_time语句执行前的阻塞时间,包含:语句解析、语句优化时间,以及作业排队时间。A1: block_time较大,而duration值并无明显变化,说明用户作业受其它作业影响,在真正开始执行前进行了较长时间的排队,下一步需要接着查看本数据表,统计起始时间小于start_time、结束时间大于finish_time的作业数量。A2: block_time较小,而duration值较大,说明用户作业执行时间增加较大原因是自己导致,需要继续分析数据量的变化情况、各DN的执行时间变化。start_time语句开始执行时间戳。finish_time语句执行结束时间戳。duration语句执行时间长度。status语句执行的结束状态,正常为finished,异常为aborted。可以查看作业是否正常结束,如果异常,还会有异常原因。abort_info语句执行结束状态为aborted时显示异常信息。min_peak_memory语句在所有DN上的最小内存峰值,单位MB。B1: 对于同一个查询,可对比前后几次的内存消耗情况,内存消耗平均值能够反映出数据表的数据量是否有变化,memory_skew_percent值能够侧面反映出相关数据表在各DN上的数据分布是否有倾斜。并且,query_plan能够直接显示作业的执行计划,对比执行计划是否有变化。max_peak_memory语句在所有DN上的最大内存峰值,单位MB。average_peak_memory语句执行过程中的内存使用平均值,单位MB。memory_skew_percent语句各DN间的内存使用倾斜率。min_spill_size若发生下盘,所有DN上下盘的最小数据量,单位MB。C1: 对有大量下盘的查询有显著帮助信息,当下盘量剧增的时候,通常是表数据量有大幅增加,或者是执行计划有问题导致的,结合query_plan能进一步分析,spill_skew_percent可以查看作业是否有严重数据倾斜。max_spill_size若发生下盘,所有DN上下盘的最大数据量,单位MB。average_spill_siz若发生下盘,所有DN上下盘的平均数据量,单位MB。spill_skew_percent若发生下盘,DN间下盘倾斜率。min_dn_time语句在所有DN上的最小执行时间,单位ms。D1: DN上的执行时间,结合duration数据,如果一个查询的DN执行时间有严重倾斜,那就需要考虑数据表的分区、分布列是否设置合适;不合理的分区、分布列,可能会导致本应分散到多个DN的执行任务被集中到个别DN上执行,执行时间必然大大增加。max_dn_time语句在所有DN上的最大执行时间,单位ms。average_dn_time语句在所有DN上的平均执行时间,单位ms。dntime_skew_percent语句在各DN间的执行时间倾斜率。min_cpu_time语句在所有DN上的最小CPU时间,单位ms。E1: CPU执行时间是分配给改作业的实际执行时间,当duration有明显增加,而平均CPU执行时间无明显变化时,很可能的一个原因是作业执行期间,有多个其它计算密集型作业同时段执行,因CPU抢占的原因,拉长了该作业的执行时长。max_cpu_time语句在所有DN上的最大CPU时间,单位ms。total_cpu_time语句在所有DN上的CPU总时间,单位ms。cpu_skew_percent语句在DN间的CPU时间倾斜率。min_peak_iops语句在所有DN上的每秒最小IO峰值。F1: IO是变化最莫测的一个资源,一个作业在数据量不变、内存消耗无变化、CPU执行时间无变化、下盘量无变化的情况下,偏偏duration增加了,那最可能的原因是IO的原因。IO有点独特的是,往往IOPS变小反而反应了作业受其它作业影响,IO跑步起来,拖长了作业执行时间;其它属性通常相反,如:内存、CPU、下盘量,这些值变小通常意味着作业执行变快了。max_peak_iops语句在所有DN上的每秒最大IO峰值。average_peak_iops语句在所有DN上的每秒平均IO峰值。iops_skew_percent语句在DN间的IO倾斜率。query_plan语句的执行计划。G1: 作业执行计划是否有变化。总结一下:因数据量变化,导致作业执行时间增加,可以分析A2/B1/D1/G1,进而确认作业查询的数据表是否有明显的数据量增加;因其它并发作业抢占,导致作业排队,从而导致作业执行时间增加,可以分析A1/B1/D1,进而查看作业执行的同时期是否有大量并发作业在执行;因其它作业而产生的CPU抢占,导致作业执行时间增加,可以分析A2/D1/E1,进而查看作业执行的同时期是否有大量并发作业在执行;因其它作业而产生的IO抢占,导致作业执行时间增加,可以分析A2/F1,进而查看作业执行的同时期是否有大量并发作业在执行;值得注意的是,发生资源争抢时,可能会出现并发症,即CPU、IO抢占,作业排队现象都会发生,针对并发症问题,可以逐步分析解决,比如:第一步,调整作业执行顺序,减少并发作业数量,减少阻塞时间;第二步,定位出同时段执行的典型计算密集型、存储密集型作业,先移动到其它时间段执行,减少对本作业的影响;第三步,在无其他作业明显干预的情况下,做进一步分析,功能二:历史用户资源占用如果无其它作业影响,TopSQL一张数据表基本已经能够分析出性能劣化缘由;但如果分析出受其它作业影响,那么接下来就是查找可能造成影响的作业。除了在TopSQL中查询执行周期内的作业信息之外,还可以借助历史用户资源占用系统表GS_WLM_USER_RESOURCE_HISTORY,来搜索“可疑”用户。“可疑”用户通常对数据库性能优化没有太多理解,往往会出现“select *”查询,或者一次提交大批量作业。GS_WLM_USER_RESOURCE_HISTORY系统表记录了所有用户的历史资源占有情况,结合反馈性能劣化的用户名以及作业执行时间段,从历史用户资源占用表中或许可以分析出是否有“可疑”用户影响。数据表GS_WLM_USER_RESOURCE_HISTORY提供的关键信息简述如表格,管理员能够分析的可能现象也在表格中:字段名称字段描述分析出可能的现象username用户名。timestamp监控时间戳。used_memory该用户正在使用的内存大小,单位MB。A: 是否有其它用户占用大量内存,结合运行作业数量分析,是一个大查询还是多个小查询。used_cpu该用户正在使用的CPU核数。B: 是否有其它用户占用大量CPU。used_space该用户已使用的存储空间大小,单位KB。C: 查看各用户的磁盘占用情况,结合负载管理(WLM)中的空间管控能力,可疑避免差SQL一次将磁盘占满的情况。used_temp_space该用户已使用的临时存储空间大小,单位KB。used_spill_space该用户已使用的算子落盘存储空间大小,单位KB。read_kbytes监控周期内,读操作的字节流量,单位KB。D: 是否有其它用户占用了大量IO资源。write_kbytes监控周期内,写操作的字节流量,单位KB。read_speed监控周期内,读操作的字节速率,单位KB/s。write_speed监控周期内,写操作的字节速率,单位KB/s。历史用户资源占用数据表能够非常直观的看出哪个用户占用了资源,而且是占用了哪类资源,管理员可疑进一步分析这些资源占用是否合理,进而通过资源管理(WLM)的管控能力,做合理的用户资源划分。功能三:历史实例资源监视在TopSQL、用户资源占用的数据表的基础上,基本能够分析出劣化原因,从而能做出相应的措施。此外,有一类问题比较独特,危害较大,DN负载不均衡或者DN劣化(硬件缘由),在数据表分布不均的情况下,可能会导致一系列SQL都会出现执行倾斜的情况,变相拉长所有作业的执行时间,TopSQL中相关SQL的倾斜值较大。针对此类问题,如果没有用户提出作业变慢的情况下,管理员如何能够提前预防呢?GaussDB 提供了记录CN、DN资源使用量的能力,该类数据会保存到GS_WLM_INSTANCE_HISTORY数据表中,包含:CPU、内存、IO等信息。如下列表所示:字段名称字段描述分析出可能的现象instancename实例名称。timestamp时间戳。used_cpu实际使用的CPU。A: 可能有个别DN长时间占用大量CPU,明显的数据倾斜特征。used_mem实际使用的内存大小。io_await实例所使用磁盘的io_wait值(10秒均值)。B1: io_util&io_await能够反应出磁盘的繁忙程度,disk_read&disk_write是发生的实际IO流量值,如果磁盘很繁忙,但实际IO流量值不高,可以进一步分析磁盘是否有坏道,是否有硬件故障。B2: 如果磁盘很繁忙,实际IO流量也很高,但是process_read&process_write却较低,说明造成磁盘繁忙的原因并不是该GaussDB实例,可能是备机catchup或者其它运行在该磁盘上的程序消耗了大量IO,可做进一步定位。B3: 通常情况下,logical_read/logical_write远大于process_read/process_write,这是因为磁盘预读+较好的缓存命中率导致的;如果两者相近,说明缓存命中率很低,进而分析是否需要vacuum或者数据表的定义是否符合查询的就近原则。io_util实例所使用磁盘的io_util值(10秒均值)。disk_read实例所使用磁盘的读速率(10秒均值),单位KB/s。disk_write实例所使用磁盘的写速率(10秒均值),单位KB/s。process_read实例对应进程从磁盘读数据的读速率(不包括从磁盘pagecache中读取的字节数,10秒均值),单位KB/s。process_write实例对应进程向磁盘写数据的写速率(不包括向磁盘pagecache中写入的字节数,10秒均值),单位KB/s。logical_read该实例在本次统计间隙(10秒)内逻辑读字节速率,单位KB/s。logical_write该实例在本次统计间隙(10秒)内逻辑写字节速率,单位KB/s。总结:本文从用户提出作业变慢这一问题作为出发点,从管理员视角,对已经发生的问题做定位定界,GaussDB 具备将瞬息万变的负载情况记录下来,提供回看数据库系统内部资源负载情况的能力。本文的管理员从作业、用户、DN三个层次,自上而下的顺序层层分析性能劣化的缘由。当然,读者可以从任意视角、以任意顺序去分析系统负载情况。本文重点是介绍了GaussDB 负载管理(WLM)提供的资源监视能力,结合所提供的监控项,能够分析出一些有趣的资源争抢现象,便于读者理解监控项的含义,方便读者对监控项的二次利用。那么,下一篇将会接着介绍负载管理(WLM)所提供的其它能力,如:存储空间管理、计算资源管理等,敬请期待,谢谢。原文链接:https://bbs.huaweicloud.com/blogs/177679【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [SQL] GaussDB(DWS)性能调优系列实战篇二:十八般武艺之坏味道SQL识别
    【摘要】 GaussDB在执行SQL语句时,会对其性能表现进行分析和记录,通过视图和函数等手段呈现给用户。本文将简要介绍如何利用GaussDB提供的这些“第一手”数据,分析和定位SQL语句中存在的性能问题,识别和消除SQL中的“坏味道”。SQL语言是关系型数据库(RDB)的标准语言,其作用是将使用者的意图翻译成数据库能够理解的语言来执行。人类之间进行交流时,同样的意思用不同的措辞会产生不同的效果。类似地,人类与数据库交流信息时,同样的操作用不同的SQL语句来表达,也会导致不同的效率。而有时同样的SQL语句,数据库采用不同的方式来执行,效率也会不同。那些会导致执行效率低下的SQL语句及其执行方式,我们称之为SQL中的“坏味道”。         下面这个简单的例子,可以说明什么是SQL中的坏味道。图1-a 用union合并集合         在上面的查询语句中,由于使用了union来合并两个结果集,在合并后需要排序和去重,增加了开销。实际上符合dept_id = 1和dept_id > 2的结果间不会有重叠,所以完全可以用union all来合并,如下图所示。图1-b 用union all合并集合         而更高效的做法是用or条件,在扫描的时候直接过滤出所需的结果,不但节省了运算,也节省了保存中间结果所需的内存开销,如下图所示。图1-c 用or条件来过滤结果         可见完成同样的操作,用不同的SQL语句,效率却大相径庭。前两条SQL语句都不同程度地存在着“坏味道”。         对于这种简单的例子,用户可以很容易发现问题并选出最佳方案。但对于一些复杂的SQL语句,其性能缺陷可能很隐蔽,需要深入分析才有可能挖掘出来。这对数据库的使用者提出了很高的要求。即便是资深的数据库专家,有时也很难找出性能劣化的原因。         GaussDB在执行SQL语句时,会对其性能表现进行分析和记录,通过视图和函数等手段呈现给用户。本文将简要介绍如何利用GaussDB提供的这些“第一手”数据,分析和定位SQL语句中存在的性能问题,识别和消除SQL中的“坏味道”。◆ 识别SQL坏味道之自诊断视图         GaussDB在执行SQL时,会对执行计划以及执行过程中的资源消耗进行记录和分析,如果发现异常情况还会记录告警信息,用于对原因进行“自诊断”。用户可以通过下面的视图查询这些信息:•       gs_wlm_session_info•       pgxc_wlm_session_info•       gs_wlm_session_history•       pgxc_wlm_session_history         其中gs_wlm_session_info是基本表,其余3个都是视图。gs_开头的用于查看当前CN节点上收集的信息,pgxc_开头的则包含集群中所有CN收集的信息。各表格和视图的定义基本相同,如下表所示。表1 自诊断表格&函数字段定义名称类型描述datidoid连接后端的数据库OID。dbnametext连接后端的数据库名称。schemanametext模式的名字。nodenametext语句执行的CN名称。usernametext连接到后端的用户名。application_nametext连接到后端的应用名。client_addrinet连接到后端的客户端的IP地址。 如果此字段是null,它表明通过服务器机器上UNIX套接字连接客户端或者这是内部进程,如autovacuum。client_hostnametext客户端的主机名,这个字段是通过client_addr的反向DNS查找得到。这个字段只有在启动log_hostname且使用IP连接时才非空。client_portinteger客户端用于与后端通讯的TCP端口号,如果使用Unix套接字,则为-1。query_bandtext用于标示作业类型,可通过GUC参数query_band进行设置,默认为空字符串。block_timebigint语句执行前的阻塞时间,包含语句解析和优化时间,单位ms。start_timetimestamp with time zone语句执行的开始时间。finish_timetimestamp with time zone语句执行的结束时间。durationbigint语句实际执行的时间,单位ms。estimate_total_timebigint语句预估执行时间,单位ms。statustext语句执行结束状态:正常为finished,异常为aborted。abort_infotext语句执行结束状态为aborted时显示异常信息。resource_pooltext用户使用的资源池。control_grouptext语句所使用的Cgroup。min_peak_memoryinteger语句在所有DN上的最小内存峰值,单位MB。max_peak_memoryinteger语句在所有DN上的最大内存峰值,单位MB。average_peak_memoryinteger语句执行过程中的内存使用平均值,单位MB。memory_skew_percentinteger语句各DN间的内存使用倾斜率。spill_infotext语句在所有DN上的下盘信息:None:所有DN均未下盘。All: 所有DN均下盘。[a:b]: 数量为b个DN中有a个DN下盘。min_spill_sizeinteger若发生下盘,所有DN上下盘的最小数据量,单位MB,默认为0。max_spill_sizeinteger若发生下盘,所有DN上下盘的最大数据量,单位MB,默认为0。average_spill_sizeinteger若发生下盘,所有DN上下盘的平均数据量,单位MB,默认为0。spill_skew_percentinteger若发生下盘,DN间下盘倾斜率。min_dn_timebigint语句在所有DN上的最小执行时间,单位ms。max_dn_timebigint语句在所有DN上的最大执行时间,单位ms。average_dn_timebigint语句在所有DN上的平均执行时间,单位ms。dntime_skew_percentinteger语句在各DN间的执行时间倾斜率。min_cpu_timebigint语句在所有DN上的最小CPU时间,单位ms。max_cpu_timebigint语句在所有DN上的最大CPU时间,单位ms。total_cpu_timebigint语句在所有DN上的CPU总时间,单位ms。cpu_skew_percentinteger语句在DN间的CPU时间倾斜率。min_peak_iopsinteger语句在所有DN上的每秒最小IO峰值(列存单位是次/s,行存单位是万次/s)。max_peak_iopsinteger语句在所有DN上的每秒最大IO峰值(列存单位是次/s,行存单位是万次/s)。average_peak_iopsinteger语句在所有DN上的每秒平均IO峰值(列存单位是次/s,行存单位是万次/s)。iops_skew_percentinteger语句在DN间的IO倾斜率。warningtext显示告警信息。queryidbigint语句执行使用的内部query   id。querytext执行的语句。query_plantext语句的执行计划。node_grouptext语句所属用户对应的逻辑集群。         其中的query字段就是执行的SQL语句。通过分析每个query对应的各字段,例如执行时间,内存,IO,下盘量和倾斜率等等,可以发现疑似有问题的SQL语句,然后结合query_plan(执行计划)字段,进一步地加以分析。特别地,对于一些在执行过程中发现的异常情况,warning字段还会以human-readable的形式给出告警信息。目前能够提供的自诊断信息如下:◇多列/单列统计信息未收集         优化器依赖于表的统计信息来生成合理的执行计划。如果没有及时对表中各列收集统计信息,可能会影响优化器的判断,从而生成较差的执行计划。如果生成计划时发现某个表的单列或多列统计信息未收集,warning字段会给出如下告警信息:Statistic Not Collect:schemaname.tablename(column name list)         此外,如果表格的统计信息已收集过(执行过analyze),但是距离上次analyze时间较远,表格内容发生了很大变化,可能使优化器依赖的统计信息不准,无法生成最优的查询计划。针对这种情况,可以用pg_total_autovac_tuples系统函数查询表格中自从上次分析以来发生变化的元组的数量。如果数量较大,最好执行一下analyze以使优化器获得最新的统计信息。◇SQL未下推         执行计划中的算子,如果能下推到DN节点执行,则只能在CN上执行。因为CN的数量远小于DN,大量操作堆积在CN上执行,会影响整体性能。如果遇到不能下推的函数或语法,warning字段会给出如下告警信息:SQL is not plan-shipping, reason : %s◇Hash连接大表做内表         如果发现在进行Hash连接时使用了大表作为内表,会给出如下告警信息:PlanNode[%d] Large Table is INNER in HashJoin \"%s\"目前“大表”的标准是平均每个DN上的行数大于100,000,并且内表行数是外表行数的10倍以上。◇大表等值连接使用NestLoop         如果发现对大表做等值连接时使用了NestLoop方式,会给出如下告警信息:PlanNode[%d] Large Table with Equal-Condition use Nestloop\"%s\"目前大表等值连接的判断标准是内表和外表中行数最大者大于DN的数量乘以100,000。◇数据倾斜         数据在DN之间分布不均匀,可导致数据较多的节点成为性能瓶颈。如果发现数据倾斜严重,会给出如下告警信息:PlanNode[%d] DataSkew:\"%s\", min_dn_tuples:%.0f, max_dn_tuples:%.0f目前数据倾斜的判断标准是DN中行数最多者是最少者的10倍以上,且最多者大于100,000。◇代价估算不准确         GaussDB在执行SQL语句过程中会统计实际付出的代价,并与之前估计的代价比较。如果优化器对代价的估算与实际的偏差很大,则很可能生成一个非最优化的计划。如果发现代价估计不准确,会给出如下告警信息:"PlanNode[%d] Inaccurate Estimation-Rows: \"%s\" A-Rows:%.0f, E-Rows:%.0f目前的代价由计划节点返回行数来衡量,如果平均每个DN上实际/估计返回行数大于100,000,并且二者相差10倍以上,则认定为代价估算不准。◇Broadcast量过大         Broadcast主要适合小表。对于大表来说,通常采用Hash+重分布(Redistribute)的方式效率更高。如果发现计划中有大表被广播的环节,会给出如下告警信息:PlanNode[%d] Large Table in Broadcast \"%s\"目前对大表广播的认定标准为平均广播到每个DN上的数据行数大于100,000。◇索引设置不合理  如果对索引的使用不合理,比如应该采用索引扫描的地方却采用了顺序扫描,或者应该采用顺序扫描的地方却采用了索引扫描,可能会导致性能低下。索引扫描的价值在于减少数据读取量,因此认为索引扫描过滤掉的行数越多越好。如果采用索引扫描,但输出行数/扫描总行数>1/1000,并且输出行数>10000(对于行存表)或>100(对于列存表),则会给出如下告警信息:PlanNode[%d] Indexscan is not properly used:\"%s\", output:%.0f, filtered:%.0f, rate:%.5f顺序扫描适用于过滤的行数占总行数比例不大的情形。如果采用顺序扫描,但输出行数/扫描总行数<=1/1000,并且输出行数<=10000(对于行存表)或<=100(对于列存表),则会给出如下告警信息:PlanNode[%d] Indexscan is ought to be used:\"%s\", output:%.0f, filtered:%.0f, rate:%.5f◇下盘量过大或过早下盘         SQL语句执行过程中,因为内存不足等原因,可能需要将中间结果的全部或一部分转储的磁盘上。下盘可能导致性能低下,应该尽量避免。如果监测到下盘量过大或过早下盘等情况,会给出如下告警信息:•       Spill file size large than 256MB•       Broadcast size large than 100MB•       Early spill•       Spill times is greater than 3•       Spill on memory adaptive•       Hash table conflict         下盘可能是因为缓冲区设置得过小,也可能是因为表的连接顺序或连接方式不合理等原因,要结合具体的SQL进行分析。可以通过改写SQL语句,或者HINT指定连接方式等手段来解决。         使用自诊断视图功能,需要将以下变量设成合适的值:▲ use_workload_manager(设成on,默认为on)▲ enable_resource_check(设成on,默认为on)▲ resource_track_level(如果设成query,则收集query级别的信息,如果设成operator,则收集所有信息,如果设成none,则以用户默认的log级别为准)▲ resource_track_cost(设成合适的正整数。为了不影响性能,只有执行代价大于resource_track_cost语句才会被收集。该值越大,收集的语句越少,对性能影响越小;反之越小,收集的语句越多,对性能的影响越大。)         执行完一条代价大于resource_track_cost后,诊断信息会存放在内存hash表中,可通过pgxc_wlm_session_history或gs_wlm_session_history视图查看。         视图中记录的有效期是3分钟,过期的记录会被系统清理。如果设置enable_resource_record=on,视图中的记录每隔3分钟会被转储到gs_wlm_session_info表中,因此3分钟之前的历史记录可以通过gs_wlm_session_info表或pgxc_wlm_session_info视图查看。◆ 发现正在运行的SQL的坏味道         上一节提到的自诊断视图可以显示已完成SQL的信息。如果要查看正在运行的SQL的情况,可以使用下面的视图:•       gs_wlm_session_statistics•       pgxc_wlm_session_statistics         类似地,gs_开头的用于查看当前CN节点上收集的信息,pgxc_开头的则包含集群中所有CN收集的信息。两个视图的定义与上一节的自诊断视图基本相同,使用方法也基本一致。 通过观察其中的字段,可以发现正在运行的SQL中存在的性能问题。         例如,通过“select queryid, duration from gs_wlm_session_statistics order by duration desc limit 10;”可以查询当前运行的SQL中,已经执行时间最长的10个SQL。如果时间过长,可能有必要分析一下原因。图2-a 通过gs_wlm_session_statistics视图发现可能hang住SQL         查到queryid后,可以通过query_plan字段查看该SQL的执行计划,分析其中可能存在的性能瓶颈和异常点。图2-b 通过gs_wlm_session_statistics视图查看当前SQL的执行计划         再下一步,可以结合等待视图等其他手段定位性能劣化的原因。图2-c 通过gs_wlm_session_statistics视图结合等待视图定位性能问题         另外,活动视图pg_stat_activity也能提供一些当前执行SQL的信息。◆ Top SQL——利用统计信息发现SQL坏味道         除了针对逐条SQL进行分析,还可以利用统计信息发现SQL中的坏味道。另一篇文章“Unique SQL特性原理与应用”中提到的Unique SQL特性,能够针对执行计划相同的一类SQL进行了性能统计。与自诊断视图不同的是,如果同一个SQL被多次执行,或者多个SQL语句的结构相同,只有条件中的常量值不同。这些SQL在Unique SQL视图中会合并为一条记录。因此使用Unique SQL视图能更容易看出那些类型的SQL语句存在性能问题。         利用这一特性,可以找出某一指标或者某一资源占用量最高/最差的那些SQL类型。这样的SQL被称为“Top SQL”。         例如,查找占用CPU时间最长的SQL语句,可以用如下SQL:select unique_sql_id,query,cpu_time from pgxc_instr_unique_sql order by cpu_time desc limit 10。         Unique SQL的使用方式详见https://bbs.huaweicloud.com/blogs/197299。◆ 结论         发现SQL中的坏味道是性能调优的前提。GaussDB对数据库的运行状况进行了SQL级别的监控和记录。这些打点记录的数据可以帮助用户发现可能存在的异常情况,“嗅”出潜在的坏味道。从这些数据和提示信息出发,结合其他视图和工具,可以定位出坏味道的来源,进而有针对性地进行优化。原文链接:https://bbs.huaweicloud.com/blogs/197413【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [SQL] Unique SQL特性原理与应用
    1  什么是Unique SQL用户执行SQL语句时,每一个SQL语句文本都会进入解析器(Parser),生成“解析树”(parse tree)。遍历解析树中各个结点,忽略其中的常数值,以一定的算法结合树中的各结点,计算出来一个整数值,用来唯一标识这一类SQL,这个整数值被称为Unique SQL ID,Unique SQL ID相同的SQL语句属于同一个“Unique SQL”。例如,用户先后输入如下两条SQL语句:select * from t1 where id = 1;select * from t1 where id = 2;这两条SQL语句除了过滤条件的常数值不同,其他地方都相同,由此生成的解析树的拓扑结构完全相同,故Unique SQL ID也相同。因此两条语句属于如下同一个Unique SQL:select * from t1 where id = ?;GaussDB内核会对所有上面形式的SQL语句汇总统计信息,通过视图呈现给用户。通过这种方式,可以排除一些无关的常量值的干扰,获得某一类SQL语句的统计数据,为性能分析和问题定位提供数值依据。注意,对于Unique SQL ID的计算,只会排除常数值,而不会排除其他的差异。例如,SQL语句“select * from t2 where id = 1;” 与上面的SQL不属于同一个Unique SQL,不同用户,从不同的CN节点执行的相同的SQL语句也不属于同一个Unique SQL。2  Unique SQL如何统计    收到SQL请求后,GaussDB内核首先算出其Unique SQL ID。如果该Unique SQL ID已存在,则直接更新相关的统计信息。如果不存在,首先创建一个Unique SQL,然后再更新统计信息,如下图所示:Unique SQL的统计信息包括执行次数,响应时间,Cache/IO数量,行活动和时间分布等信息,可以通过如下两个视图查询:gs_instr_unique_sqlpgxc_instr_unique_sql前者显示当前CN(Coordinator Node)节点(执行当前SQL命令的节点)上的Unique SQL信息,后者显示系统中所有CN节点上的Unique SQL信息。两个视图的格式相同,均由下表中的字段组成:字段名称字段类型解释node_namenameUnique SQL来源CN的名称node_idintegerUnique SQL来源CN的ID(等同于pgxc_node表中的node_id)user_namename执行SQL语句的用户名称user_idoid执行SQL语句的用户OIDunique_sql_idbigint归一化的Unique SQL IDquerytext归一化的Unique SQL字符串n_callsbigint调用次数min_elapse_timebigintSQL在内核内的最小运行时间(单位:微秒)max_elapse_timebigintSQL在内核内的最大运行时间(单位:微秒)total_elapse_timebigintSQL在内核内的总运行时间(单位:微秒)n_returned_rowsbigintSELECT返回的结果集行数n_tuples_fetchedbigint随机扫描行数n_tuples_returnedbigint顺序扫描行数n_tuples_insertedbigint插入行数n_tuples_updatedbigint更新行数n_tuples_deletedbigint删除行数n_blocks_fetchedbigintbuffer的块访问次数n_blocks_hitbigintbuffer的块命中次数n_soft_parsebigint软解析次数, n_soft_parse + n_bard_parse可能大于n_calls, 因为子查询未计入n_callsn_hard_parsebigint硬解析次数, n_soft_parse + n_bard_parse可能大于n_calls, 因为子查询未计入n_callsdb_timebigint有效的DB时间花费,多线程将累加(单位:微秒)cpu_timebigintCPU时间(单位:微秒)execution_timebigint执行器内执行时间(单位:微秒)parse_timebigintSQL解析时间(单位:微秒)plan_timebigintSQL生成计划时间(单位:微秒)rewrite_timebigintSQL重写时间(单位:微秒)pl_execution_timebigintplpgsql上的执行时间(单位:微秒)pl_compilation_timebigintplpgsql上的编译时间(单位:微秒)net_send_timebigint网络上的时间花费(单位:微秒)data_io_timebigintIO上的时间花费(单位:微秒) 3  如何使用Unique SQL使用Unique SQL功能需要打开以下变量开关:enable_resource_check(默认为on)track_counts(默认为on,影响行活动和Cache/IO相关字段)此外还需要将instr_unique_sql_count设为正整数。该变量默认为0,且不能在gsql会话中修改,需要通过SIGHUP的方式设置,例如:gs_guc reload -Z coordinator -D /path/to/coordinator1/ -c "instr_unique_sql_count=20" > /dev/nullinstr_unique_sql_count参数决定了系统收集的unique sql的数量。当收集的unique数量达到这个数后,新的sql不再被收集。如果将该数值改大,原有的unique sql信息保留,同时开始收集新的unique sql。如果将该数值改小,则会清空当前CN节点所有已收集的unique sql信息,然后开始收集新的unique sql。设置好上述变量后,Unique sql统计视图可以像普通视图一样查询,例如:postgres=# select node_name,query,n_calls from pgxc_instr_unique_sql;  node_name   |                           query                            | n_calls--------------+------------------------------------------------------------+--------- coordinator2 | select node_name,query,n_calls from pgxc_instr_unique_sql; |       0(1 row)系统函数reset_instr_unique_sql可以清理unique sql信息,该函数有3个参数,含义如下:1.   scope:如果为"GLOBAL",则清除所有CN节点上的数据;如果为"LOCAL",只清空当前CN上的数据。2.   type:如果为“ALL”,则清除所有数据;如果为"BY_USERID",只清除指定用户的unique SQL;如果为"BY_CNID",只清除指定CN的unique SQL。3.   value:如果type=“ALL”,该参数无意义;如果type="BY_USERID",该参数为指定用户的ID,如果type="BY_CNID",该参数为指定CN的ID。例如:postgres=# select reset_instr_unique_sql('global','all',0); reset_instr_unique_sql------------------------ t(1 row)         此外,如果数据库进程重启,也会导致之前收集的unique SQL信息被清空。4  用Unique SQL辅助定位问题unique sql视图提供了丰富的信息,用户可以根据需要选取对自己有帮助的信息使用。本节针对客户在生产环境中遇到的实际情况,举例说明几种该视图的使用方法,可供性能优化参考。4.1  查询异常的行活动导致的磁盘争用异常的行活动可能引起磁盘争用,导致业务运行缓慢。通过查看扫描的行数、返回的函数、更改的行数等指标的波动情况,可以发现异常的行活动,帮助定位原因。postgres=# select sum(n_returned_rows) n_returned_rows, sum(n_tuples_fetched) n_tuples_fetched,    sum(n_tuples_returned) n_tuples_returned, sum(n_tuples_inserted) n_tuples_inserted,    sum(n_tuples_updated) n_tuples_updated, sum(n_tuples_deleted) n_tuples_deleted from pgxc_instr_unique_sql; n_returned_rows | n_tuples_fetched | n_tuples_returned | n_tuples_inserted | n_tuples_updated | n_tuples_deleted-----------------+------------------+-------------------+-------------------+------------------+------------------             234 |                0 |                 0 |                 0 |                0 |                0(1 row) 4.2  查询Top SQL对资源的占用情况可以基于执行时间、CPU时间、扫描行数、物理读/逻辑读等指标,对unique SQL视图中的SQL语句进行排序,找出占用资源最多的那些SQL语句,有针对性地其分析对性能的影响和原因,帮助查找和定位问题。例如,·           按SQL执行时间顺序或倒序排序:SELECT user_name, unique_sql_id, query, total_elapse_time FROM pgxc_instr_unique_sql ORDER BY total_elapse_time ASC 或 DESC;·           按SQL执行占用CPU时间进行顺序或倒序排序:SELECT user_name, unique_sql_id, query, cpu_time FROM pgxc_instr_unique_sql ORDER BY cpu_time ASC 或 DESC;·           按SQL顺序扫描行数顺序或倒序排序:SELECT user_name, unique_sql_id, query, n_tuples_returned FROM pgxc_instr_unique_sql ORDER BY n_tuples_returned ASC 或 DESC;·           按SQL总扫描行进行顺序或倒序排序:SELECT user_name, unique_sql_id, query, n_tuples_fetched + n_tuples_returned FROM pgxc_instr_unique_sql ORDER BY n_tuples_fetched + n_tuples_returned ASC 或 DESC;·           按SQL执行执行器时间进行顺序或倒序排序:SELECT user_name, unique_sql_id, query, execution_time FROM pgxc_instr_unique_sql ORDER BY execution_time ASC 或 DESC;·           按SQL执行物理读次数进行顺序或倒序排序:SELECT user_name, unique_sql_id, query, n_blocks_fetched FROM pgxc_instr_unique_sql ORDER BY n_blocks_fetched ASC 或 DESC;·           按SQL执行逻辑读次数进行顺序或倒序排序:SELECT user_name, unique_sql_id, query, n_blocks_hit FROM pgxc_instr_unique_sql ORDER BY n_blocks_hit ASC 或 DESC;4.3  查询逻辑读/物理读数量逻辑读/物理读过多可能导致SQL语句占用较多的CPU时间。通过查询unique SQL视图可以得到sql语句逻辑/物理读数据块的数量,辅助判断响应过慢的原因:·           查询物理读块数量:SELECT n_blocks_fetched FROM pgxc_instr_unique_sql;·           查询逻辑读块数量:SELECT n_blocks_hit FROM pgxc_instr_unique_sql;4.4  诊断内存配额不足导致性能低下如果数据库缓冲区设置得太小,会导致每个SQL语句执行的结果不能被缓存,当前SQL执行完毕如果有其他SQL执行就会把内存中上一个或上几个SQL缓存的执行结果挤出去,下一轮如果当前这个SQL再次执行时候又需要从磁盘进行物理IO读取数据,而不能直接从缓存中获取数据,进而导致SQL执行性能较差。缓冲区配额是否足够大,可以通过命中率来判断。缓冲区命中率=n_blocks_hit/n_blocks_fetched,可以通过查询unique SQL来诊断是否存在内存配额不足的问题:SELECT (n_blocks_hit/ n_blocks_fetched) AS hit_ratio from pgxc_instr_unique_sql;原文链接:https://bbs.huaweicloud.com/blogs/197299【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [SQL] GaussDB(DWS) TD和Oracle兼容模式的差异
    【摘要】 GaussDB(DWS) TD和Oracle两种兼容模式的差异,以及对每种差异做了举例说明。GaussDB(DWS)支持两种兼容模式,即TD(Teradata)兼容模式、ORA(Oracle)兼容模式。可以在CREATE DATABASE时通过指定选项DBCOMPATIBILITY进行选择。语法如下:--创建兼容TD的数据库 postgres=# CREATE DATABASE td_compatible_db DBCOMPATIBILITY 'TD';CREATE DATABASE--创建兼容ORA的数据库 postgres=# CREATE DATABASE ora_compatible_db DBCOMPATIBILITY 'ORA';CREATE DATABASEpostgres=# SELECT datname,datcompatibility FROM PG_DATABASE WHERE datname LIKE '%compatible_db';       datname      | datcompatibility  -------------------+------------------  td_compatible_db  | TD  ora_compatible_db | ORA(2 rows)两种兼容模式的注意差异对比如下表格所示:下面对每一个兼容性进行举例说明:-- 切到TD兼容的库下,创建表并插入数据 postgres=# \c td_compatible_db td_compatible_db=# CREATE TABLE td_table(a INT,b VARCHAR(5),c date);NOTICE:  The 'DISTRIBUTE BY' clause is not specified. Using 'a' as the distribution column by default.HINT:  Please use 'DISTRIBUTE BY' clause to specify suitable data distribution column.CREATE TABLEtd_compatible_db=# INSERT INTO td_table VALUES(1,null,CURRENT_DATE);   INSERT 0 1td_compatible_db=# INSERT INTO td_table VALUES(2,'',CURRENT_DATE);  INSERT 0 1-- 区分空串和NULL,date类型只显示年月日td_compatible_db=# SELECT a, b, b IS NULL AS null, c FROM td_table;  a | b | null |     c       ---+---+------+------------  1 |   | t    | 2020-06-19  2 |   | f    | 2020-06-19(2 rows)td_compatible_db=# SELECT CURRENT_DATE;     date     ------------  2020-06-19(1 row)-- 空串转int,转为0。TD数据库不同于Oracle,Oracle将空串当做NULL进行处理,TD在将空串转换为数值类型的时候,默认将空串转换为0进行处理,因此查询空串会查询到数值为0的数据。同样地,在TD兼容模式下,字符串转换数值的过程中,也会将空串默认转换为相应数值类型的0值进行处理。除此之外,' - '、' + '、' '这些字符串也都会在TD兼容模式下默认转换为0进行处理,但是小数点字符串' . '会报错td_compatible_db=# SELECT b::int FROM td_table WHERE b = '';     b  --- 0(1 row)--超长字符自动截断。当连接到TD兼容的数据库时,td_compatible_truncation参数设置为on时,将启用超长字符串自动截断功能,在后续的insert语句中(不包含外表的场景下),对目标表中char和varchar类型的列上插入超长字符串时,系统会自动按照目标表中相应列定义的最大长度对超长字符串进行截断。td_compatible_db=# SHOW td_compatible_truncation;  td_compatible_truncation  -------------------------- on(1 row)td_compatible_db=# INSERT INTO td_table VALUES(3,'12345678',CURRENT_DATE);INSERT 0 1td_compatible_db=# SELECT * FROM td_table WHERE a = 3;                      a |   b   |     c       ---+-------+------------  3 | 12345 | 2020-06-19(1 row)--varchar   + int运算,转为numeric + numeric计算td_compatible_db=# EXPLAIN VERBOSE SELECT b + a FROM td_table WHERE a = 3;                                           QUERY PLAN                                           ----------------------------------------------------------------------------------------------- Data Node Scan  (cost=0.00..0.00 rows=0 width=0)    Output: (((td_table.b)::numeric + (td_table.a)::numeric))    Node/s: datanode7    Remote query: SELECT b::numeric + a::numeric AS "?column?" FROM public.td_table WHERE a = 3(4 rows)-- case和coalesce表达式。对于case 和coalesce,在TD 兼容模式下的处理● 如果所有输入都是相同的类型,并且不是unknown类型,那么解析成这种类型。● 如果所有输入都是unknown类型则解析成text类型。● 如果输入字符串(包括unknown,unknown当text来处理)和数字类型,那么解析成字符串类型,如果是其他不同的类型范畴,则报错。● 如果输入类型是同一个类型范畴,则选择该类型的优先级较高的类型。● 把所有输入转换为所选的类型。如果从给定的输入到所选的类型没有隐式转换则失败。示例1:Union中的待定类型解析。这里,unknown类型文本'b'将被解析成text类型。td_compatible_db=# SELECT text 'a' AS "text" UNION SELECT 'b';text------ab(2 rows)示例2:简单Union中的类型解析。文本1.2的类型为numeric,而且integer类型的1可以隐含地转换为numeric,因此使用这个类型。td_compatible_db=# SELECT 1.2 AS "numeric" UNION SELECT 1;numeric---------11.2(2 rows)示例3:转置Union中的类型解析。这里,因为类型real不能被隐含转换成integer,但是integer可以隐含转换成real,那么联合的结果类型将是real。td_compatible_db=# SELECT 1 AS "real" UNION SELECT CAST('2.2' AS REAL);real------12.2(2 rows)示例4:TD模式下,coalesce参数输入int和varchar类型,那么解析成varchar类型。ORA模式下会报错。查看coalesce参数输入int和varchar类型的查询语句的执行计划如下td_compatible_db=# EXPLAIN VERBOSE select coalesce(a, b) FROM td_table;                                          QUERY PLAN                                          --------------------------------------------------------------------------------------------- Data Node Scan  (cost=0.00..0.00 rows=0 width=0)    Output: (COALESCE((td_table.a)::character varying, td_table.b))    Node/s: All datanodes    Remote query: SELECT COALESCE(a::character varying, b) AS "coalesce" FROM public.td_table(4 rows)原文链接:https://bbs.huaweicloud.com/blogs/176361【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [SQL] GaussDB(DWS)的explain performance详解
    在SQL调优过程中,经常使用explain performance,查看某个执行比较慢的SQL语句的实际执行信息和估算信息,通过对比实际执行与优化器的估算之间的差别,找到执行中的瓶颈点,来为优化提供依据。Explain performance的结果包括七部分,分别为:以表格形式显示的计划Predicate Information (identified by plan id)Memory Information (identified by plan id)Targetlist Information (identified by plan id)DataNode Information (identified by plan id)User Define Profiling====== Query Summary =====下面,以8个DN,数据量为1TB的GaussDB中执行tpcds的Q67为例,对这7部分分别进行详细介绍。具体的SQL语句及查询计划参考附件Q67.txt。以表格形式显示的计划表格字段解读:id:执行算子节点编号。该编号只是为了唯一标识每个算子,不代表算子的执行顺序。operation:具体的执行节点算子名称。常用的算子参见下面的常用算子介绍章节。A-time:当前算子执行完成时间,一般DN上执行的算子的A-time是由[]括起来的两个值,分别表示此算子在所有DN上完成的最短时间和最长时间。一般,算子的A-time中包含其下子节点的执行时间。比如:  Id为20号的Vector Sort算子的A-time中的第二个值,其A-time = 该算子本身的执行时间 + 21号算子的A-time,由此可以计算出来,20号算子的执行时间 = 28201.498 – 4097.214 ≈ 24000,单位为ms。  通过这种方式,就可以帮我们找到执行时间较长的算子,即瓶颈点,分析该算子是否可以优化。比如下图示例计划中从id为16到21之间部分,如下图所示。rollup函数使用sort耗时长,总耗时达到50s(即17号-20号算子的总耗时),(并行度32的情况下),20号算子Vector sort达24s,19号算子Vector Sore Aggregate达9s,18号算子做重分布达10s,17号算子hashagg达到8s。因此需要考虑对rollup类的分析函数考虑使用其它方式进行优化,比如用hashagg替代sortagg,避免大数据量排序性能降低。另外,A-time中有两个值,第一个是所有DN中执行该算子用时最短的时间,第二个是所有DN中执行该算子用时最长的时间。当这两个值相差较大时,说明存在计算倾斜。这两个值偏差越大,表明此算子的计算倾斜(在不同DN上执行时间差异)越大,人工干预调优的必要性越大。  导致计算倾斜的原因,可能是数据在各DN上分布存在倾斜(可通过select * from table_distribution(‘schema_name’, ‘table_name’);查看表在各DN上的数据分布情况),也可能是DN之间的资源配置有差异,也可能是分布列设置不合理等。对于stream算子来说,它的A-time比较特殊,stream算子主要是接收子节点的数据。它的子节点是在计划开始执行时,就启动多线程并发执行,而不是等着父节点向其请求数据时才触发执行。所以在stream的父节点向stream节点请求数据时,它的子节点如果已经准好了数据,那么stream节点的实际执行时间就是接收数据的时间,因此有时可以看到stream算子的A-time比其子节点的A-time小,如上图中的12号算子。A-rows:表示当前算子实际输出的全局元组数,即所有DN输出的元组数之和。如果是复制表,则此列的值=表中总行数*DN数。当要多次读取某个算子的执行结果,比如,nestloop中,外表中的每条数据都要扫描一遍内表的数据,即内表数据要被多次rescan,此时,A-rows显示的是多次loop之后的行数。E-rows:每个算子估算的输出行数。A-row和E-row的差异体现了优化器估算和实际执行的偏差度。一般来说,偏差越大,越可以认为优化器生成的计划越不可信,人工干预调优的必要性越大。如果估算不准,可能会导致如下的几种问题:采取不正确的连接方式。比如把内表数据估计太小,可能会导致使用性能不好的nestloop方式进行连接搞反内外表。如果估计的内表数量较小,外表数量较大,但实际内表数量大,外表数量小,就会导致数据量大的表作为了内表,数量小的表作为了外表。导致连接性能不好。采用不正确的重分布方式。如果要被分布的数据被估计的太小,会使得计划采用boardcast方式对数据进行重分布,当实际数据很大时,会导致数据在DN之间传输耗时较多。连接中选取数量大的表做重分布。下图就是一个错误选择大表做重分布的例子。E-distinct:表示单DN上hashjoin算子的distinct估计值。这一列有两个值,第一个值代表外表的distinct值,第二个值代表内表的distinct值。将来会将这两个值分别显示在内表和外表对应的行数,便于理解。Peak Memory:此算子在每个DN上执行时使用的内存峰值。当在SMP场景中,该列是单线程的数据。这点需要改进一下,应该显示单DN上所有线程peak memory的和比较合理,便于调优时合理设置内存。SMP的介绍参考SMP特性章节。E-memory:DN上每个算子估算的内存使用量,只有DN上执行的算子会显示。某些场景会在估算的内存使用量后使用括号显示该算子在内存资源充足下可以自动扩展的内存上限。A-width:表示当前算子每行元组的实际宽度,仅对于重内存使用算子会显示,包括:(Vec)HashJoin、(Vec)HashAgg、(Vec) HashSetOp、(Vec)Sort、(Vec)Materialize算子等,其中(Vec)HashJoin计算的宽度是其右子树算子的宽度,会显示在其右子树上。使用括号显示该算子输出元组中的最小和最大宽度。E-width:每个算子输出元组的估算宽度。E-costs:每个算子估算的执行代价。Predicate Information (identified by plan id)  这部分主要显示的是谓词信息,即在整个计划执行过程中不会变的信息,主要是一些join条件和一些filter信息。  下图中,对这部分进行了说明。Memory Information (identified by plan id)  这一部分显示的是整个计划中会将内存的使用情况打印出来的算子的内存使用信息,主要是Hash、Sort算子,包括:算子峰值内存(peak memory)DataNode Query Peak Memory显示每个DN节点在整个查询过程中使用的内存峰值。它们中的最大值经常用来估算SQL语句耗费的内存,也被用来作为SQL语句调优时运行态内存参数设置的重要依据。算子内的peak memory显示算子内每个DN节点使用的内存峰值。控制内存(control memory)一般出现在hash join、hash agg算子中,用于创建hash表和hash探测所使用的内存估算的内存使用(estimate memory)执行时实际宽度(width)内存使用自动扩展次数(auto spread times)是否提前下盘(early spilled),及下盘信息,包括重复下盘次数(spill Time(s)),内外表下盘分区数(inner/outer partition spill num),下盘文件数(temp file num),下盘数据量及最小和最大分区的下盘数据量(written disk IO [min, max] )。提前下盘是指还有可用内存,但不足以支撑接下来的操作。主要在以下情况会发生:当hash表中剩余的内存小于要插入数据申请的内存根据当前操作的内存使用判断该操作是一个非常耗内存操作时。比如大数据量的sort操作。此时就要看一下当前配置的work_mem是否太小。Targetlist Information (identified by plan id)这部分显示的是每一个算子输出的目标列。格式如下:输出的目标列一般是:查询中显示指定的输出列分组、排序、过滤条件、连接条件中出现的列。这些非显示指定的输出列,在查询的最后不会输出,但是在执行的中间过程中被输出给其它算子用于以上操作。比如下图中的store_sales.ss_sold_date_sk列就是只用于连接条件。  对于输出列信息中还有一点需要说明的是,某些需要经过计算的表达式列,比如下图19号算子中的sum表达式列,在19号算子中每个DN计算了这个表达式的结果,在上层18号streaming算子中只是引用19号算子的结果进行重分布数据,不对其进行计算,所以在18号算子中在该sum表达式两边加了一对圆括号,表示是对下层节点中该表达式结果的引用,不再重复计算。DataNode Information (identified by plan id)  这部分会将各个算子的执行时间、CPU、buffer的使用情况全部打印出来。  如果算子采用了SMP执行,则会详细列出DN上每个线程的情况,如下图:  Buffer有三种类型,分别为:Shared buffer:用于普通表数据Temp buffer:用于临时文件中的数据Local buffer:用于临时表数据  Buffer的使用情况包括read(从外存读入buffer数)、written(从buffer写出到外存数)、hit(数据被读入buffer后,再次被访问次数)、dirtied(buffer中内容被修改的buffer数)。其中temp buffer只会统计read和written情况。如下是一个对buffer使用情况的说明。User Define Profiling  这部分显示的是CN和DN、DN和DN建连的时间,以及存储层的一些执行信息。这里涉及到很多名词,此处做个简单介绍:建连(build connection)是指,不同节点间(CN和DN、DN和DN)需要传输数据,而建立的连接。这一般只有stream算子才会有。CU(Compression Unit),压缩单元。列存表的最小存储单位。Vector batch,向量批。存放参与向量计算的一批数据。  下面分别是Q67的查询计划树和user define profiling,可以通过对照计划树,便于了解user define profiling中各个plan node id对应的算子操作。====== Query Summary ===== 这部分主要打印一些查询总结信息。包括:DataNode executor start time:DN上执行器的开始时间第一个括号中是两个DN的名字,第一个是执行器开始时间最短的DN,第二个是执行器开始时间最长的DN第二个括号中是对应第一个括号中两个DN的执行器启动时间Datanode executor end time: DN上执行器的结束时间后面两个括号中的含义类似DN上执行器的开始时间,分别代表执行器结束时间最短和最长的DN名字,及其对应的结束用时Remote query poll time: stream gather算子用于监听是否有各DN数据到达CN的网络poll时间System available mem: 当前预计执行时系统可用内存Query Max mem: 查询执行所需最大内存Query estimated mem: 查询执行所需使用内存估计Avail/Max core: 可用/最大CPU核数Cpu util: 最大CPU数Active statement: 当前语句生成计划时,GaussDB(DWS)上正在运行的其它语句数Query estimated cpu: 计划的CPU使用估计,它是首先找出所有stream算子中cpu使用最多的cpu使用值(此处简写为max_cpu_usage),然后用所有stream算子的cpu使用之和/max_cpu_usage计算得出Mem allowed dop: 内存允许的dop限制。是根据DN所在主机的空闲内存情况、主机上DN个数、计划中stream个数、当前可用的CPU数及估计要使用的CPU数计算出来最大dop数。如果设置了query_dop不为0的值,则dop不能超过query_dop的限制,具体参考如何开启SMP。如果query_dop设置为自适应,则dop不能超过GaussDB(DWS)支持的最大dop(即Min non-spill dop)。Min non-spill dop: dop不能超过此限制。限制为64Initial dop: 初始dopFinal dop: 最终dopCoordinator executor start time: CN上执行器的启动用时Coordinator executor run time: CN上执行器的运行用时Coordinator executor end time: CN上执行器的结束用时Total network : 网络通信总共传输的数据量Planner runtime: 生成计划的时间Query Id: 该查询的query id,用来唯一标识该查询,CN和DN上同一个查询的query id相同,以便于查询其他视图中标识属于同一查询的不同节点上的信息Total runtime: 整个查询的总用时相关知识介绍常用算子介绍  算子主要分为以下五类:控制算子。控制算子是一类用于处理特殊情况的节点,用于实现特殊的执行流程。算子类型描述Result处理含有仅需一次计算的条件表达式或INSERT语句中 VALUES子句指定的将要插入的元组Append用于表示和组织需要包含多个子查询执行流程BitmapAnd用于需要对两个或多个位图进行并操作的流程BitmapOr用于需要对两个或多个位图进行或操作的流程RecursiveUnion用于处理WITH子句中递归定义的UNION子查询扫描算子。扫描类算子一般是执行计划树的叶子节点,不仅可以扫描表,还可以扫描函数的结果集、Values链表结构、子查询结果集等,每次获取一条元组作为上层节点的输入。算子类型描述SeqScan顺序扫描,用于行存表Cstore Scan列存表扫描IndexScan基于索引扫描,通过索引找到物理表中的元组IndexOnlyScan基于索引扫描,直接从索引返回元组BitmapScan(BitmapIndexScan, BitmapHeapScan)利用bitmap获取元组TidScan通过元组tid获取元组SubqueryScan子查询扫描FunctionScan处理范围表中含有函数的扫描ValuesScan用于Values链表扫描CteScan用于扫描CommonTableExprWorkTableScan用于扫描RecursiveUnion迭代的中间数据ForeignScan外部表扫描物化算子。物化算子是一类可以缓存元组的算子。在执行过程中,很多扩展的物理操作符需要首先获取所有的元组才能进行操作(例如聚集函数操作、没有索 引辅助的排序等),这是要用物化算子将元组缓存起来。算子类型描述Material对子查询结果进行缓存。对于需要重复多次扫描的子节点,特别是扫描 结果每次都相同时,可以减少执行的代价Sort对下层算子返回的元组进行排序,该算子只有左子节点Group对下层排序元组进行分组操作。用于处理GROUP BY子句,分组后只返回该分组的第一个元组。该算子只有一个左子节点,且子节点必须返回在分组属性上已排好序的元组Agg用于执行聚集函数Unique执行去重操作HashHashjoin辅助节点,将从Hashjoin左子节点获取的元组放入构造好的Hash表中,Hash算子也只有一个左子节点SetOp处理集合操作Exist、Intersect查询Limit处理Limit/offset子句,从下层节点的输出中挑选处于一定范围内的元组WindowAgg处理窗口函数连接算子。连接算子对应于关系代数中的连接操作。连接算子按实现方式可以分为:Nestloop、HashJoin、 MergeJoin算子类型执行方式限制优势劣势适用情况Nestloop循环连接。对于外表的每一行,嵌套扫描内表返回结果无当内表使用索引时,可以快速定位连接元组每个外表均需重新执行内节点操作外表结果集小HashJoinHash连接。内表根据join列建立hash表,外表使用相同hash值仅匹配相应hash桶连接两端必须为类型相同的 等值连接,且支持hash散列通过哈希散列,一次性定位 连接元组内表在内存放不下可能导致 使用多轮hash,列重复值太 多可能导致分桶内表可在内存里放下,列重 复值和倾斜不要太多MergeJoin归并连接。内外表均排序后,进行排序后的归并连接操作(1)等值连接(2)内外表有序(否则需要排序)通过归并连接,一次性定位连接元组内外表需要有序,因此必须承受内外表IndexScan或Sort的代价内外表已有有序,不需要重新排序Streaming是一个特殊的算子,它实现了分布式架构的核心数据shuffle功能,Streaming共有三种形态,分别对应了分布式结构下不同的数据shuffle功能:Streaming (type: GATHER):作用是CN从DN收集数据。Streaming(type: REDISTRIBUTE):作用是DN根据选定的分布列把数据重分布到所有的DN。Streaming(type: BROADCAST):作用是把当前DN的数据广播给其他所有的DN针对以上算子,如果出现了Vector前缀的算子是指向量化执行引擎算子,一般出现在含有列存表的Query中。SMP特性  SMP特性通过算子并行来提升性能,同时会占用更多的系统资源,包括CPU、内存、网络、I/O等等。本质上SMP是一种以资源换取时间的方式,计划并行之后必定会引起资源消耗的增加,当上述资源成为瓶颈的情况下,SMP无法提升性能,反而可能导致性能的劣化。在出现资源瓶颈的情况下,建议关闭SMP。  在使用了SMP特性的查询计划中,可能会看到类似Streaming(type: SPLIT REDISTRIBUTE dop: 10/10)的算子,这其中的dop是degree of parallel的缩写,后面的两个数字分别表示该算子在每个DN上执行时的线程数,和其子节点执行时的线程数。SMP适用的场景支持并行的算子计划中存在以下算子支持并行:Scan:支持行存普通表和行存分区表顺序扫描、列存普通表和列存分区表顺序扫描、HDFS内外表顺序扫描;支持GDS数据导入的外表扫描并行。以上均不支持复制表。Join:HashJoin、NestLoopAgg:HashAgg、SortAgg、PlainAgg、WindowAgg(只支持partition by,不支持order by)。Stream:Redistribute、Broadcast其他:Result、Subqueryscan、Unique、Material、Setop、Append、VectoRow、RowToVecSMP特有算子为了实现并行,新增了并行线程间的数据交换Stream算子供SMP特性使用。这些新增的算子可以看做Stream算子的子类。Local Gather:实现DN内部并行线程的数据汇总Local Redistribute:在DN内部各线程之间,按照分布键进行数据重分布Local Broadcast:将数据广播到DN内部的每个线程Local RoundRobin:在DN内部各线程之间实现数据轮询分发Split Redistribute:在集群跨DN的并行线程之间实现数据重分布Split Broadcast:将数据广播到集群所有DN的并行线程上述新增算子可以分为Local与非Local两类,Local类算子实现了DN内部并行线程间的数据交换,而非Local类算子(即stream算子)实现了跨DN的并行线程间的数据交换。如何开启SMP使用SMP特性通过设置query_dop参数的值来控制。query_dop=1(默认值),表示不启用SMP。query_dop=0(自适应),系统会根据资源情况和计划特征,动态为每个查询选取[1,8]之间的最优的并行度,最大化提升查询性能。query_dop=-value,在考虑资源情况和计划特征基础上,限制dop选取的范围为[1,value]。query_dop=value,不考虑资源情况和计划特征,强制选取dop为1或value。原文链接:https://bbs.huaweicloud.com/blogs/193434【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [SQL] 华为云数仓GaussDB(DWS):内存自适应控制技术解密
    【摘要】 GaussDB(DWS)引入了内存自适应控制的技术,在SQL语句复杂、处理数据量大的AP场景下,能够对运行的作业进行内存级的管控,避免高并发场景下内存不足产生的各种问题。1. 技术背景在SQL语句复杂、处理数据量大的AP场景下,单个查询对内存的需求越来越大,多个语句的并发很容易将系统的内存吃满,造成内存不足的问题。为了应对这种问题,GaussDB(DWS)引入了内存自适应控制的技术,在上述场景下能够对运行的作业进行内存级的管控,避免高并发场景下内存不足产生的各种问题。2. GaussDB(DWS)的静态内存管理机制及缺陷GaussDB(DWS)的执行引擎继承自PG,对于优化器生成的执行计划树,总体采取执行算子+流水线的处理方式,如下图所示。对于NestLoop算子节点,需要首先从左树的IndexScan算子节点获取元组,然后到右子树的IndexScan算子节点进行连接,匹配元组后进行输出。流水线的执行方式使得对于NestLoop, IndexScan类的一般算子,同时只有一定数量的元组处于内存中,对于行引擎每个算子仅占用一条元组的空间,对于列引擎占用一个batch(最多1000条元组)的空间,占用的空间较小,基本可以忽略不计。但是,GaussDB(DWS)中也有一些需要将所有数据收集后进行处理的算子,在执行时需要使用较多的内存,通常我们称这类算子为物化算子。GaussDB(DWS)中主要存在如下不同种类的物化算子:(1) HashJoin:Hash连接操作符,主要思想是计算左右两表连接列的hash值,通过hash值比较减少元组比较的次数,需要将一个表建立hash表,另一个表进行hash值比较操作,建立hash表需要在内存中进行。(2) HashAgg:Hash聚集操作符,主要思想同HashJoin类似,通过hash值比较减少元组去重比较的次数,需要将不同值的元组保存的内存中。(3) Sort:排序操作符,需要获取所有元组后进行排序操作,待排序元组均存在于内存中。(4) Materialize:物化操作符,通常在需要重复扫描时使用,通过将结果存储在内存中,保证重复扫描时的效率。同时,GaussDB也提供下盘的机制,当上述操作符需要使用的内存太大时,可以将部分或全部的数据下盘处理,提高内存的使用效率,但相应的查询性能也会受到影响。PG使用 work_mem参数来控制算子可使用内存的阈值,当使用内存超过阈值时,就需要做下盘处理。GaussDB(DWS)的静态内存管理机制也延续了PG的处理机制,使用work_mem来控制单算子的内存使用上限。GaussDB(DWS)的静态内存管理存在较大弊端,需要调优人员能够根据数据量、语句复杂程度和系统的内存大小设置合理的work_mem,既避免work_mem设置太大导致系统资源不够用,还要考虑到数据规模,保证大部分算子不下盘。通常情况下,这个是很难做到的,有以下几点原因:(1) 通常情况下,复杂语句的执行计划中包含多个复杂算子,每个算子的内存使用上限是work_mem,我们没有办法计算一个语句要使用多少内存,因此也就不容易设置一个最优的work_mem参数,保证尽可能不下盘,同时内存又够用。并发场景更无法设置了。(2) work_mem只是每个算子内存使用的上限,并不是预分配;如果数据量没有那么大的话,实际内存使用是达不到work_mem的。因此也会影响work_mem的设置。(3) 每个语句的场景不一样,有的语句包含多个物化算子,而另外的语句只有一个物化算子,而这个算子对内存的需求会比较大,因此无法全局统一地进行设置。3.  GaussDB(DWS)的内存自适应技术介绍针对静态内存管理机制的弊端,我们设计了内存自适应控制技术,目的有两个:(1) 去除静态内存管理对work_mem的依赖。可以由SQL引擎优化器模块自动估算每个算子所需的内存。(2) 避免大并发场景下内存不足现象的发生。资源管理模块根据SQL引擎优化器对于每个查询内存的估算值,对每个查询进行调度,如果超过系统可用内存,则进行排队。     如上图所示,动态资源管理与内存自适应技术的组件图如上图所示。我们从多个CN中选择一个CN,命名为CCN(Central CN),进行语句队列的管理。对于每个查询SQL,CN在生成完执行计划后,为每个物化算子分配合适的内存,同时计算整个语句内存使用量,并将语句及对应的内存使用量发给CCN。CCN维护系统可用的内存值,对于新来的语句,如果语句内存使用量小于可用内存值,则允许其下发到DN执行,否则挂起,等到有语句结束释放内存后再次将其唤醒,是否可以下发。     为了达到上述目的,SQL引擎实现了内存自适应控制技术,步骤如下:(1)对于每个SQL,生成计划前首先从资源管理模块获取系统当前的最大可用内存(Query Max Mem)和当前可用内存(System Available Mem)。最大可用内存通常为每个DN的最大可用内存去除系统预分配内存,例如:数据缓存等,表示语句可用的最大内存,如果语句使用内存超过该值,必须下盘。当前可用内存用于表示当前系统的繁忙程度,如果当前可用内存比较小,倾向于选择耗费内存少的计划。(2)依据当前可用内存生成计划,同时根据SQL引擎优化器计划生成过程中的cost估算值估算每个物化算子的内存使用量,以及流水线场景下整个查询使用的内存总量估算值。如果该值大于当前可用内存,则尝试将整个查询的内存使用量调到当前可用内存以下,此时会造成部分算子下盘。(3)将语句及估算的语句内存发送到CCN,如果当前可用内存小于语句估算内存,则估算语句的内存进一步减少是否对查询性能造成较大的影响,如果根据cost评估影响不大,则进一步减少算子的内存使用,使语句内存使用满足当前可用内存,将语句下发执行,否则则进入排队状态。(4)由于每个算子的内存使用量是基于cost评估获得,可能存在一定的误差。因此,在SQL语句执行时,支持内存的动态调整,包括:执行算子内存的自动扩展和提前下盘。当算子达到估算的内存值上限,但系统还有宽裕的内存时,会进行算子内存的扩展,继续保持不下盘的状态。当系统已用内存达到80%或更高时,如果算子已有最小内存保证,则会触发提前下盘逻辑,保证不会由于内存不足而报错。4.  GaussDB(DWS)内存自适应的使用和参数控制通过开启use_workload_manager和enable_dynamic_workload两个参数开启GaussDB(DWS)的内存自适应控制机制。使用内存自适应机制时,打印SQL语句的explain performance执行计划运行信息时,会包含以下额外的信息辅助定位问题:(1) 在最下方的Query Summary一栏中,会显示出System available mem、Query max mem和Query estimated mem,分别表示:系统当前可用内存、语句可用最大内存(系统可用最大内存),语句估算内存使用量,均为单DN的衡量值。下图表示当前语句的语句最大可用内存和系统当前可用内存均为22G,语句估算内存使用为1.6G。                                        (2) 在Memory Information一栏,会显示CN和每个DN的内存使用峰值,如下图所示,语句实际内存使用,单DN使用16GB,CN使用76MB。                       (3) 在Memory Information一栏下方每个算子对应的位置,会显示每个算子单DN的内存峰值,同时会显示每个DN上内存使用的自动扩展和提前下盘情况,例如下图,可以看出第15号HashJoin算子,每个SMP线程的内存使用均为3.8GB,估算内存是860MB,经历了五次内存自动扩展,在第五次扩展后,系统内存告急,算子未用到第五次扩展后的峰值即提前下盘。               (4) 在explain performance最顶层的表格中,汇总了每个算子的估算内存和实际使用内存的情况,见下图的E-memory和Peak Memory两列所示。与上面信息对应,第15号算子单SMP线程的peak memory,最大值为3766MB,最小值为3753MB,估算内存值(单DN4个SMP线程)为860MB。     可以看出,上面例子由于cost估算不准导致内存估算值较小,实际场景也会出现内存估算值较大的场景,会导致CCN预留内存较多,阻塞其它作业的执行。因此,可以使用参数query_mem来控制语句最大可用内存上限(单DN),相当于代替了Query max mem。此参数默认为0,表示未开启。当此值大于32MB(最小语句内存分配值)时,表示开启,此时使用work_mem控制系统当前可用内存进行估算,相当于代替了System available mem进行估算。此时,CCN会使用query_mem值进行语句内存估算值的预留和排队,提高并发场景下的内存使用效率。5. 总结    内存自适应控制技术是GaussDB(DWS)的资源管理结合SQL引擎所做的一次尝试,当然还存在一些不足,比如:cost估算对内存的评估影响较大,部分场景存在失真需要进行参数控制;系统中内存使用情况比较复杂,还存在部分内存不在管控范围内需要增强。欢迎各位在实用过程中,将遇到的各种问题及时反馈,也帮助我们更好的改进!原文链接:https://bbs.huaweicloud.com/blogs/176326【推荐阅读】【最新活动汇总】DWS活动火热进行中,互动好礼送不停(持续更新中)  HOT  【博文汇总】GaussDB(DWS)博文汇总1,欢迎大家交流探讨~(持续更新中)【维护宝典汇总】GaussDB(DWS)维护宝典汇总贴1,欢迎大家交流探讨(持续更新中)【项目实践汇总】GaussDB(DWS)项目实践汇总贴,欢迎大家交流探讨(持续更新中)【DevRun直播汇总】GaussDB(DWS)黑科技直播汇总,欢迎大家交流学习(持续更新中)【培训视频汇总】GaussDB(DWS) 培训视频汇总,欢迎大家交流学习(持续更新中)扫码关注我哦,我在这里↓↓↓
  • [技术干货] s下bat批处理执行Mysql的sql语句
    有时候我们需要用bat来定时执行mysql那么就可以参考下面的代码 直接上代码:123456789101112131415161718192021@ECHO OFF  SET dbhost=主机名(例如:127.0.0.1)SET dbuser=用户名(例如:root)SET dbpasswd=用户密码(例如:root)SET dbName=数据库名称(例如:test)SET sqlpath=%~dp0(此语句可以保证.bat同级目录下的.sql文件能被找到)set sqlfile=update.sql(需要执行执行sql的文件) 进入mysql安装路径的bin目录下,如果配置了环境变量则不需要此语句 (例如:cd /d C:\Program Files\MySQL\MySQL Server 5.5\bin) ::执行SQL脚本 mysql -h%dbhost% -u%dbuser% -p%dbpasswd% < %sqlpath%%sqlfile% --default-character-set=utf8 ECHO 完成!PAUSE @ECHO Done!windows下执行sql文件-批量执行sql语句新建一个txt文件,里面内容如下,改为.cmd文件,点击运行即可:123456789101112rem MySQL_HOME 本地MySQL的安装路径rem host mysql 服务器的ip地址,可以是本地,也可以是远程rem port mysql 服务器的端口,缺省为3306rem user password 具有操作数据库权限的用户名和密码,如rootrem default-character-set 数据库所用的字符集rem database 要连接的数据名,这里用的testrem test.sql 要执行的脚本文件,这里为test.sqlrem mysql 后面的应该放在一行。set MySQL_HOME=C:\mysql-4.1.10-win32set PATH=%MySQL_HOME%\bin;%PATH% mysql --host=192.168.0.66 --port=3306 --user=root --password=123 --default-character-set=utf8 test<test.sqlWindows下批处理执行MySQL脚本文件一、1234567891011121314151617@echo offSetlocal enabledelayedexpansion::CODER BY Mark_Li POWERD BY iBAT 1.6cd "C:\Program Files\MySQL\MySQL Server 5.5\bin":: 数据库名称@set db=hrms:: 用户名@set userName=root:: 密码@set password=:: 要执行的sql脚本@set sqlpath="C:\Program Files\MySQL\MySQL Server 5.5\test_hrms.sql":: 连接MySQL数据库并执行sql脚本 -f 脚本执行过程中,出现错误继续执行 --default-character-set指定导入数据的编码(与数据库编码相同)mysql -f -u %userName% --password=%password% %db% < %sqlpath% --default-character-set=gbk:: 执行完成后,不立刻关闭dos窗口 pause二、设置超时命令在my.ini文件下加入wait_timeout=2880000interactive_timeout = 2880000max_allowed_packet = 100M三、如果要执行多个SQL脚本将test_hrms.sql替换为source "C:\Program Files\MySQL\MySQL Server 5.5\test_hrms.sql" "C:\Program Files\MySQL\MySQL Server 5.5\test_hrms2.sql""C:\Program Files\MySQL\MySQL Server 5.5\test_hrms3.sql"