环境背景
因为工作需要,需要使用数据泵将测试环境数据按照指定日期导出(通过日期过滤掉部分历史数据),导出过程中遇到了字符转义的问题。这里专门挑选2个案例,在测试环境进行测试。另外,还对两种案例使用parfile的方式进行测试。
本次测试选择的操作系统版本为RedHat6.5,Oracle数据库版本为11.2.0.4,数据库为单机单实例文件系统部署。
案例简介
案例一:
过滤子句的字符转义,如INCLUDE,EXCLUDE,QUERY等,这里选择QUERY子句进行测试。这也是实际开发测试过程中使用频率较高的功能。
案例二:
测试表名大小写敏感,且使用特殊符号“$”。
案例一:数据过滤子句转义
对于本案例,选择了对使用parfile和不使用parfile两个场景的测试。
场景1:直接在服务器端执行命令,不使用parfile
(1)按照expdp命令规范设计导出语句,原句(无转义)执行情况如下
(2)根据上述错误信息,对QUERY子句中的左右括号加上转义字符,并执行
(3)这个错误有点莫名其妙,猜测是双引号的问题,对QUERY子句中的双引号加上转义字符,并执行
(4)根据新的错误信息,提示错误的子句前方有个“
(5)看着有点像那么回事了,不过还是存在错误。看报错信息,只能是yyyy-mm-dd两侧的单引号有问题了,这次对QUERY子句中所有单引号加上‘\’并执行
执行很顺利。回顾一下,上文一共对括号、单引号、双引号、大于号、小于号等特殊字符做了转义。
场景2:在服务器端创建parfile文件并执行expdp命令
(1)创建parfile文件,并去掉所有参数中的转义字符
(2)使用parfile参数导出
执行顺利完成。
案例二:大小写敏感且带有特殊符号'$'的转义
对于本案例,选择了对使用parfile和不使用parfile两个场景的测试。
场景1:直接在服务器端执行命令,不使用parfile
(1)创建测试表,名称小写且带有'$'字符
create table cams_core."test$escape"(id number,name varchar2(20));
(2)按照命令格式拼接导出语句执行报错
(3)显然Linux将$escape解析成为环境变量,但变量是个空值,所以提示ORA-39166和ORA-31655的错误。这里还测试了多组值,无一例外全部报错。
tables=test\$escape
tables="test$escape"
tables='"test$escape"'
tables=\'\"test$escape\"\'
(4)经过多次验证,正确的写法为tables='\"test$escape\"'
执行顺利完成。回顾一下,这里对tables参数使用了单引号包含双引号的方式,以保证系统能将"test$escape"解析成为小写字母和'$'混合的字符串。同时,按照Linux的要求对双引号增加转义。
场景2:在服务器端创建parfile文件并执行expdp命令
(1)创建parfile文件,并去掉所有参数中的转义字符
(2)使用parfile参数导出
执行顺利完成。
总结分析
(1)在Linux下执行expdp或者impdp命令且带有INCLUDE,EXCLUDE,QUERY等子句时,需要对括号、单引号、双引号、大于号、小于号等特殊字符做转义。
(2)在Linux下执行expdp或者impdp命令,如果需要导出名字较为特殊的表,可以使用单引号包含双引号的方式导出,但需要对双引号做转义。
(3)使用parfile可以避免转义的问题,减少很多不必要的麻烦。另外,还可以复用parfile,减少数据泵敲命令的时间。
各位读者朋友也可关注作者微信公众号“IT技术佳肴”,与作者交流。