在大型数据清洗和复杂业务流程中,SQL代码经常需要分为多个小步骤来执行。当这些代码很长,达到数百甚至数千行时,复用它们需要修改许多参数,复用脚本不方便。为解决此问题,可以将这些代码改写成存储过程,从而将参数控制在可管理的范围内。但手动改写和调试这些长SQL为存储过程是一项极其繁琐和耗时的任务。因此,我希望通过Python自动化这个过程,希望提高10倍以上效率,可以节约时间,减少错误,还有非常重要的一点是节约我们的宝贵的注意力。
可以将存储过程分解为以下三个部分:
-
开始:这包括定义参数和初始化过程,例如:
- 创建存储过程
- 添加功能名称、参数等注释
- 使用DECLARE声明变量
- 使用BEGIN开始存储过程
-
中间:这是存储过程的主体,包括:
- 将SQL语句封装为变量
- 使用RAISE通知执行状态
- 执行封装后的SQL
-
结尾:这包括选择语言、添加存储过程注释等,例如:
- 发送完成的通知
- 添加return、END标签
- 选择存储过程语言(例如plpgsql、python)
- 修改存储过程所有者
- 添加存储过程注释
考虑到开始和结尾部分的内容基本固定,可以创建一个模板,只需要替换中间部分即可。因此具备可行性。
- 创建固定的模板,用于存储过程的开头和结尾。
- 替换中间的SQL脚本,需要注意:
- 单引号转义
- 时间、日期和表名的替换
- 将SQL封装为变量
- 合并所有部分。
为确保转换过程的准确性,SQL使用需要满足以下格式要求:
- 每段SQL语句都应以分号结尾。
- 在“create table as”语句前,应有“drop if exists”语句。
- 在“insert into”语句前,应有“delete from”语句。
- 时间查询条件推荐使用“between and”格式,以方便程序识别。
- 有时间、日期偏移相关的脚本,用注释打上偏移或offset字样,程序会选择偏移相关的参数。
文件结构:
- main.py: 主执行脚本。
- config_files/: 存放其他必要文件
- 正则替换参数.csv: 正则替换参数
- SP_Snippet_Begin.sql: SQL模板
- file_utils/: 文件操作相关的文件夹。
- reader.py: 读取文件相关的函数。
- writer.py: 写入文件相关的函数。
- sql_processors/: SQL处理文件夹,包含与SQL处理相关的模块。
- replacer.py: 与SQL内容替换相关的函数。
- encapsulator.py: 封装SQL的函数。
- generator.py: 与生成存储过程相关的函数。
- results/:默认结果路径,可通过界面选择其他文件夹路径,结果文件格式为SP_sp的名称。
- original_files/:存放sql或txt原始脚本文件,如SQL_text.sql。可通过按钮自定义选择
- 运行main.py,弹出GUI界面
python main.py
- 图形界面填写相关信息
- 点击运行
- 在结果文件夹找到转为存储过程(SP)的脚本
将SQL语句转换为存储过程具有一定挑战性,目前大部分常见SQL转SP都可以自动处理。这个项目是一步一步做起来的,我自己有相关需求场景,碰到问题一步步优化。期间,碰到的主要难点有以下3个:
- 难点一在于抽象总结存储过程步骤。
- 难点二在于正则表达式编写,SQL语句写法样式很多,非常考验文本抽取识别信息的能力,对正则表达式要求很高。
- 难点三在于很多细节调优,完成一版自己可用的程序相对容易,要对外发布使用就需要解决那行不太重要但也常见的问题。
目前语句可完成90%的SQL转存储过程操作,对于那些不能自动处理的特殊情况,转换后可以进行手动调整即可。
2024-04-07 改为GUI图形交互界面,方便更多人使用
2023-08-22 修改 encapsulator.py,解决不封闭语句块(如有create无drop语句)无法正确识别或识别后输出顺序不对情况
2023-08-22 大福优化,修改 encapsulator.py,解决不能识别连续多个drop语句、多个analyze语句
2023-08-22 重构为模块化代码易于维护
2023-08-14 脚本大部分是线性的和过程性的,重构函数,易于维护和扩展。
2023-02-08 优化,新增逐行替换的复杂版本,打上偏移标识别,可识别是否需要时间日期偏移。路径使用pathlib库把Windows路径转为Unix样式通用路径
2023-02-06 优化,新增全部文本替换的简单版本,正则替换整理成csv文件,读取循环匹配。时间日期匹配可采用>=、>、<、<=样式,可满足一部分人采用此种样式的替换
2022-06-20 创建,只能匹配between and 样式时间,可完成70%常规语句转化,可用但不完善,如正则写死不太灵活,识别日期、时间的样式较少