电信这头telepg的迁移主要是用datax和oracle2pg 这两款开源软件,这两款软件的部署后续记录,现在先测试下迁移:
1.oracle2pg 这款软件主要是抽取oracle的各种表结构,包括表(包含索引) 视图 存过 函数 等等
有两点要注意, 一个是外键,一个是序号
外键的话要在所有对象都迁移过去之后再创建, 序号的话要手动创建,因为oracle的max值比pg的要大,用这个sql查
select case when MAX_VALUE > 999999999999999999 then
(case CACHE_SIZE
when 0 then
'create sequence ' || lower(SEQUENCE_NAME)
|| ' INCREMENT ' || INCREMENT_BY
|| ' MINVALUE ' || MIN_VALUE
|| ' MAXVALUE ' || '999999999999999999'
|| ' START ' || LAST_NUMBER || ';'
else
'create sequence ' || lower(SEQUENCE_NAME)
|| ' INCREMENT ' || INCREMENT_BY
|| ' MINVALUE ' || MIN_VALUE
|| ' MAXVALUE ' || '999999999999999999'
|| ' START ' || LAST_NUMBER
|| ' CACHE ' || CACHE_SIZE || ';'
end)
else
(case CACHE_SIZE
when 0 then
'create sequence ' || lower(SEQUENCE_NAME)
|| ' INCREMENT ' || INCREMENT_BY
|| ' MINVALUE ' || MIN_VALUE
|| ' MAXVALUE ' || MAX_VALUE
|| ' START ' || LAST_NUMBER || ';'
else
'create sequence ' || lower(SEQUENCE_NAME)
|| ' INCREMENT ' || INCREMENT_BY
|| ' MINVALUE ' || MIN_VALUE
|| ' MAXVALUE ' || MAX_VALUE
|| ' START ' || LAST_NUMBER
|| ' CACHE ' || CACHE_SIZE || ';'
end)
end sequence_ddl
from dba_sequences where SEQUENCE_OWNER=upper('&owner_name’);
首先研究下oracle2pg这款开源组件的使用:
ora2pg是一款提取oracle端的各种对象的工具,通过配置conf文件来指定连接oracle的信息,然后把oracle端的各项元数据提取成文本文件,后续可以在pg端执行,
1.安装部署ora2pg,以及oracle的客户端
2.编辑参数文件,参数文件没有固定位置,只要编写就行,例子如下:
PG_VERSION 12
ORACLE_HOME /usr/lib/oracle/12.2/client64/
ORACLE_DSN dbi:Oracle:host=10.62.8.14;service_name=crm3yz;port=11521
ORACLE_USER system
ORACLE_PWD ctbj_2014
SCHEMA cep
PREFIX_PARTITION 1
PREFIX_SUB_PARTITION 1
FILE_PER_CONSTRAINT 1
FILE_PER_INDEX 1
FILE_PER_FKEYS 1
USE_RESERVED_WORDS 1
TRANSACTION readonly
DISABLE_UNLOGGED 1
# FILE_PER_CONSTRAINT 将导出的约束单独放在一个文件中
# FILE_PER_INDEX 将导出的索引单独放在一个文件中
# FILE_PER_FKEYS 将导出的外键放在单独的文件中
# PREFIX_PARTITION 导出的分区表加上主表文件名前缀
# PREFIX_SUB_PARTITION 同上,针对的对象是子分区
# USE_RESERVED_WORDS 如果oracle中导出的表名或列名有关键字,则导出时自动为其加上双引号,尽量询问应用看能否更改PG中的表名或字段名
# TRANSACTION readonly 设置为只读事务,避免误操作Oracle端数据
# DISABLE_UNLOGGED 禁止转换unlogged表,避免出现unlogged表
# 调用方式:ora2pg -c ora2pg.conf -t <TYPE> -o <SQL_FILE_PATH>
编写好参数文件之后就可以执行了:
# table (46/46)
cd /home/shx/ora2pg/crm3db/cep/conf
ora2pg -c ora2pg.conf -t "TABLE" -b ../sql -o cep.sql
# procedure (5/5)
ora2pg -c ora2pg.conf -t "PROCEDURE" -b ../sql -o cep_procedure.sql
# SEQUENCE (6/6)
ora2pg -c ora2pg.conf -t "SEQUENCE" -b ../sql -o cep_sequence.sql
# PACKAGE (1/1)
ora2pg -c ora2pg.conf -t "PACKAGE" -b ../sql -o cep_package.sql
-c 指定参数文件 -t指定导出的对象类型, -b 导出的文件放在哪里, -o 导出的文件的名字
导出之后的文件如下:
所以在这之前要先确认好oracle端导出的对象类型和对应的数量,注意外键最后再执行
也可以单独制定导出一张表的ddl: 后面加 -a ,可以用 ora2pg -h 来看可以执行的命令
在pg端应用:
1.先设置出错之后不自动退出:
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' cep.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' CONSTRAINTS_cep.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' FKEYS_cep.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' INDEXES_cep.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' cep_package.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' cep_procedure.sql
sed -i 's/ON_ERROR_STOP ON/ON_ERROR_STOP off/g' cep_sequence.sql
然后在pg端执行, -f是指定文件:
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f cep.sql > ../log/cep.log 2>&1
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f CONSTRAINTS_cep.sql > ../log/CONSTRAINTS_cep.log 2>&1
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f INDEXES_cep.sql > ../log/INDEXES_cep.log 2>&1
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f cep_package.sql > ../log/cep_package.log 2>&1
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f cep_procedure.sql > ../log/cep_procedure.log 2>&1
psql -h 10.62.8.156 -p 18801 -d crm3db -U cep -f cep_sequence.sql > ../log/cep_sequence.log 2>&1
接下来实验:
首先确认迁移目标:
这次实验就用汇聚库的rule用户来测试,先在汇聚库查rule用户的对象类型:
可以看到就table 和 index, 分别是111 和 117 ,接下来配置参数文件:
然后执行:
ora2pg -c rule.conf -t "TABLE" -b sql -o rule_table.sql
发现多了一些表,查一下,发现不应该查dba_segments 应该查dba_objects:
这下对上了
index的话不用单独导出,在导出table的元数据的时候就会把index也导出来,不过index的话,导出完之后的文件列表如下:
其中indexes里面只有6条的原因是,对于主键索引,pg和oracle都是在添加主键的时候就会自动创建一个索引,所以pg把主键索引全部放到了 constraints里面去自动创建了.
接下来把文件传输到对应的pg端,然后应用文件,这里我用我的测试环境了:
首先把这4个sql的set ON_ERROR_STOP 调成off
然后执行:
cd /home/postgres
psql -h 10.37.129.4 -p 1921 -d lv -U rule -f rule_table.sql > log/rule_table.log 2>&1
psql -h 10.37.129.4 -p 1921 -d lv -U rule -f INDEXES_rule_table.sql > log/INDEXES_rule_table.log 2>&1
psql -h 10.37.129.4 -p 1921 -d lv -U rule -f CONSTRAINTS_rule_table.sql > log/CONSTRAINTS_rule_table.log 2>&1
命令可以成功执行,没有任何返回信息就是成功了,检查log的话有如下显示:
不过要注意一点,这个命令里面的 -U 是指定的连接pg的用户,如果pg库有对应的schema,那就创建在这个schema上,如果没有对应的schema,就创建在默认的schema下(public)
然后索引和约束的日志也是类似,要注意如果有报错,会显示psql: 为开头的日志信息.




