实现oracle数据批量定时同步到mysql(一)
一、需求背景
整体项目为数据统计类系统,源数据库为oracle,考虑到法律风险和成本控制,需要落库为mysql,并实现定时更新功能。
二、具体实操
多的不说,具体看操作过程。 这个过程中,找了很多种实现方式和工具,目前能基本实现项目的需求,不过便利程度上还是需要斟酌。
1、主要使用到的工具
1)navicat15(这个版本能控制单次执行插入语句的数量,分批执行) 2)kettle(开源的etl工具) 3)结合些部分自己处理的工具和代码
2、实践过程
首先用navicat的数据传输功能进行异构数据库的传输 1、先配置oracle和mysql数据库的连接 mysql比较简单,oracle的话主要要下载对应操作系统(一般是x64)的oracle client客户端,把oci.dll这个文件添加进来,选择工具—选项。 好了后,选择数据传输,选择连接,这里也可以选择导出为文件(sql文件) 然后点击选项,这里有几个地方需要的 1)创建表去掉索引,外键这些 2)使用扩展插入,这样速度会比较快(但是如果全量插入,数据量比较大的话会有问题),这里我一开始操作,数据量几十万的表,一次性扩展插入,导致内存溢出,一开始是8g内存,后来加了内存到32g,就没出问题了。这里选择高级,单次1000次(这个数值可以改),但是如果表比较多的话一个个改也是个麻烦事,so后来发现有个配置文件,可以手动批量修改好,看图
这里是保存的配置文件路径
找到s.ndtfpremium文件打开看
可以发现每个表的设置就是这里的一个列表的一个元素
主要的不同也就是如下框出来的地方,我这里用excel和程序进行批量处理的 先查出oracle所有表名
SELECT table_name from all_tab_comments
where table_type='TABLE'
and owner='CSRC'
order by table_name
复制所有表名到excel中,然后给定函数
=CONCATENATE(""""&A1&"""",",")
,在用java程序处理这些表名,生成列表内容,复制s.ndtfpremium 的头部和尾部,形成这些表配置文件
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
public class Test1 {
public static void main(String[] args) throws IOException {
String[] s1 = {
"RMI_LOG_201804",
"RMI_LOG_201805"
};
fun1(s1);
}
public static void fun1(String[] s1) throws IOException {
StringBuilder s2=new StringBuilder();
for (int i = 0; i <s1.length ; i++) {
String s3="{\n" +
" \"Name\": \"";
String s4="\",\n" +
" \"ObjectType\": \"TableNormal_ORA\",\n" +
" \"Advanced\": {\n" +
" \"TargetTableName\": \"";
String s5="\",\n" +
" \"UseAllFields\": true,\n" +
" \"FieldMappings\": [],\n" +
" \"UseAllRows\": true,\n" +
" \"EnableNumberOfRowsPerBatch\": true,\n" +
" \"NumberOfRowsPerBatch\": 100,\n" +
" \"RecordsetConditions\": [],\n" +
" \"UseTransactionForEachRecordset\": true\n" +
" }\n" +
" },";
s2.append(s3);
s2.append(s1[i]);
s2.append(s4);
s2.append(s1[i]);
s2.append(s5);
s2.append("\n");
}
System.out.println(s2);
fileWriterMethod("D:\\bigdata_work\\javaWorkspace\\jeecgboot\\批量拼接字符串_navicat配置\\src\\file/s.ndtfpremium",s2.toString());
}
public static void fileWriterMethod(String filepath, String content) throws IOException {
File file = new File(filepath);
if (!file.exists()) {
file.createNewFile();
}
try (FileWriter fileWriter = new FileWriter(filepath)) {
fileWriter.append(content);
}
}
}
点击下一步开始就ok了,不过在实际运行的过程中,发现仍然会导致内存很高,跑了一段时间后,我想可能还是跟navicat本身的机制有关,可以分多次处理(比如500张表分50张表跑一次批),这样可能会好点
三、最终效果
基本的表结构和数据都能正常拿到,只不过部分类型的字段会不太美观,比如主键的number类型转化,但是也不影响开发使用就是 目前已有的条件下,只做到这样的异构数据批量同步,大家有好的实现思路和方法,也欢迎一起探讨! 后续会继续看下其他方式的更新
|