GSQL是如何让GaussDB(DWS) 像执行SHELL一样执行SQL的?GSQL的动态变量功能实践说明

举报
SeqList 发表于 2022/12/21 16:57:46 2022/12/21
【摘要】 GSQL工具目前版本支持在SQL中使用“变量”,通过SELECT语句的结果赋值到变量中,后续的SQL可以使用变量拼接,轻松实现存储过程中复杂的传参动作,同时提供简单的元命令功能,使SQL脚本能简单实现循环,使用操作系统命令等,功能强大、简单易读。

GSQL动态变量功能背景

Teradata中国客户中,大量使用一种动态sqlDsql)工具来执行SQL脚本,Dsql支持在SQL脚本中使用“变量”,通过SELECT语句的结果赋值到变量中,后续的SQL可以使用变量拼接,轻松实现存储过程中复杂的传参动作,同时提供简单的元命令功能,使SQL脚本能简单实现循环,使用操作系统命令等,功能强大、简单易读。

Teradata迁移DWS过程中,DWS客户端工具GSQL能执行一般的SQL语句脚本,无法对SQL进行传入“变量”的动作。因TeradataDsql功能强大且易用,在客户要求下,DWSGSQL进行了适配改造,使之支持动态SQL功能。

GSQL本身支持元命令,为适配Teradata Dsql的逻辑判断、循环等,新增了\if \label \goto等元命令,除此以外,还新增了for循环,更方便地实现循环逻辑,让SQL跟shell脚本一样方便快捷好用


GSQL动态变量功能使用场景

  • 迁移替换TERADATADsql

       TeradataDsql在国内普遍使用,为能顺利迁移,gsql工具对此做了适配改造,增加控制流的元命令、动态变量功能

  • 替换存储过程

        存储过程能实现变量逻辑、IF判断逻辑、语句报错等,以实现业务逻辑。但存储过程在测试、调试、调优等都比较困难,SQL较复杂时,排查问题等比较费劲。

        GSQL的动态变量功能,能覆盖存储过程的变量、判断等复杂逻辑同时,每个SQL独立执行,能很方便地调试、调优、排查问题。


GSQL动态变量功能介绍

       GSQL动态变量新增功能点

  • 变量功能    

    通过SELECT语句、\set value key的方式赋值,用于后续SQL语句使用

  • 控制功能

    通过元命令判断语句报错、跳转、退出等

  • 跳转功能

         通过元命令实现语句的跳转,以及for循环

GSQL动态变量功能常用启用命令

gsql -h <ipaddr> -p <port> -d <db> -U <user> -W <pass> -D   -e  --set-file=<a.cfg> -v k1=v1 -v k2=v2 -f  <script.sql>

gsql命令行动态变量说明如下图:

   以下是具体每个功能点的详细功能和例子说明:

GSQL动态变量功能介绍-变量功能(变量定义

动态变量定义方式 注意事项 具体方法 样例

SELECT语句定义变量

SELECT语句定义变量时,as后面若不使用双引号,数据库自动返回小写,而变量使用时是区分大小写的

直接SELECT定义变量

通过表SELECT定义变量

元命令\set语法定义

可以读取操作系统命令结果作为变量,使用``符号执行
\set 变量 值
\set 变量 `操作系统命令`
gsql 命令定义变量

GSQL启动时可以通过-v 或--set-file预置公共的变量

通过命令行增加 -v key1 = value1 方式定义变量

通过--set-file xx.cfg读取配置文件的方式定义变量


    GSQL动态变量功能介绍-变量功能(变量使用


    动态变量使用方式 说明 样例
    变量用在过滤条件上

    在SQL的过滤条件、表名、或者\if判断语法中,填写相关的变量,在GSQL启用-D 时执行,变量会自动替换为具体数值。


    变量用在表名称上
    变量用在判断语句上


    GSQL动态变量功能介绍-IF判断功能

    GSQL新增\if 判断,能轻松对报错进行异常处理,对结果判断进行不同分支处理等,以下是常用的\if判断功能例子:

    • 语句报错\if退出处理

          GSQL脚本:

             

        GSQL日志:

           

    •     IF/ELSE功能样例

           

    GSQL动态变量功能介绍-控制功能

    •     GSQL新增\goto \label 标签跳转功能

        能实现SQL块的跳转,实现复杂逻辑,如下图gsql脚本,通过不同label来实现两个不同的逻辑分支

       GSQL脚本:

             

    日志结果:

       

    • FOR循环功能

        能通过SQL的结果作为循环的输入,例子如下:

    GSQL脚本:

       

    GSQL动态变量功能介绍-常见的内置参数说明


    参数名称

    设置方法

    参数说明

    参数使用场景

    ROW_COUNT

    SQL返回的记录数,不建议手动设置

    ERROR_LEVELstatement时,表示上一条SQL语句执行返回的行数或受影响的行数。
    ERROR_LEVELtransaction时,如果事务结束时内部有错,表示事务内最后一个SQL语句执行返回的行数或受影响的行数,否则表示上一条SQL语句执行返回的行数或受影响的行数。

    该参数常用于记录数\if判断

    \if ${ROW_COUNT} == 0


    VAR_MAX_LENGTH

    \set VAR_MAX_LENGTH variable

    用于控制变量值的长度,默认为4096。如果变量值的长度超过该值,变量值会被截断,并输出告警信息。

    部分场景使用的参数比较长(如拼接SQL等),可设置64000等较长参数,最大不要超过int类型的长度

    ERROR_LEVEL

    \set ERROR_LEVEL transaction | statement

    表示ERROR标识成功或者失败类型,默认为transaction。

    statement:ERROR记录上一条SQL语句是否执行成功。
    transaction:ERROR记录上一条SQL语句是否执行成功,或上一个事务内部执行是否出错。

    需要记录事务内的SQL报错时的${ERROR}参数,将该参数修改为statement

    VAR_NOT_FOUND

    \set VAR_NOT_FOUND default | null | error

    可以设置为defaultnullerror之一以控制引用变量不存在时的处理方式。

    default:不做变量替换,保持原有字符串。
    null:将原有字符串替换为空字符串。
    error:输出报错信息,保持原有字符串。

    一般设置为null,将不存在的参数结果返回null


    COMPARE_STRATEGY

    \set COMPARE_STRATEGY default | natural | equal

    用于控制\if表达式中大小比较的策略,默认为default

    default:默认的比较策略,只支持字符串或数字比较,不支持混合比较。单引号内的按照字符串处理,单引号外的按照数字处理。
    natural:在default的基础上,包含动态变量的按照字符串处理。当比较操作符有一侧是数字,尝试将另一侧转换为数字,然后比较。如果转换失败,报错且比较结果为假。
    equal:只支持等值比较,所有情况按照字符串比较。

    \if 逻辑的比较策略,默认是不支持字符与数字的比较,一般设置为natrual让字符和数字比较。

    SQLSTATE

    SQL返回的错误代码,不建议手动设置

    ERROR_LEVELstatement时,表示上一条SQL语句执行的状态码。
    ERROR_LEVELtransaction时,如果事务结束时内部有错,表示事务内最后一个SQL语句执行的状态码,否则表示上一条SQL语句执行的状态码。

    获取报错代码用于后续处理

    ON_ERROR_ROLLBACK

    \set ON_ERROR_ROLLBACK on | interactive | off

    如果是on,当一个事务块里的语句产生错误的时候,这个错误将被忽略而事务继续。

    如果是interactive,这样的错误只是在交互的会话里忽略。

    如果是off(缺省),事务块里一个语句生成的错误将会回滚整个事务。

    事务中SQL报错需要不会滚时设置

    ON_ERROR_STOP

    \set ON_ERROR_STOP on | off

    on:命令执行错误时会立即停止,在交互模式下,gsql会立即返回已执行命令的结果。

    off(缺省):命令执行错误时将会跳过错误继续执行。


    一般设置为on,让SQL脚本执行时报错会退出,后续逻辑会继续执行,可能引起数据错误等问题

    GSQL动态变量功能实践(常见逻辑搭配)

    下面举一些常见的GSQL使用搭配例子,能更快更好地理解和使用好gsql的动态变量功能

    样例说明 SQL例子

    使用LABEL处理SQL语句报错,若报错则退出脚本

    通过操作系统命令获取变量值

    GSQL执行结果:

    GSQL的元命令本身支持导入/导出/调用SQL脚本

    批量循环创建不同名表,常见的变量场景,能轻松创建大量测试表


    最后总结一下:

     GSQL动态变量新增功能点

    • 变量功能    

      通过SELECT语句、\set value key的方式赋值,用于后续SQL语句使用

    • 控制功能

      通过元命令判断语句报错、跳转、退出等

    • 跳转功能

             通过元命令实现语句的跳转,以及for循环

    相比存储过程,更轻量,无结构,更容易调试,真的能像shell一样轻松实现多样控制、循环等功能,真心强力推荐使用!!!


    更多GSQL的用法,参考官方产品文档:

    https://support.huaweicloud.com/tg-dws/dws_gsql_002.html

    【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
    • 点赞
    • 收藏
    • 关注作者

    评论(0

    0/1000
    抱歉,系统识别当前为高风险访问,暂不支持该操作

    全部回复

    上滑加载中

    设置昵称

    在此一键设置昵称,即可参与社区互动!

    *长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

    *长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。