场景:
我有两个远程数据库(源和目标),我希望它们是相似的。我想验证这是真的还是找出目标数据库中缺少的内容 - 不一定关注converse。
我正在使用Java 1.8和OJDBC6驱动程序连接两个使用Oracle 11g的数据库。我被告知在Oracle 11g数据库上使用带有Java的ResultSet rs.next()是昂贵的,我不确定是否有更好的方法来比较数据库 - 我愿意使用工具或某种平面文件方法,如果存在。
数据:
有超过300个表,列数不同;有些表有主键,有些表没有。
我相信找出哪些表有主键而哪些表没有,这是我在SQL中执行的第一步:
---TABLES WITH PRIMARY KEY
SELECT TABLE_NAME
FROM ALL_CONSTRAINTS
WHERE OWNER = 'PLTTUX_ADMIN'
AND (CONSTRAINT_TYPE = 'P')
ORDER BY TABLE_NAME;
.
---TABLES WITHOUT PRIMARY KEY
SELECT TABLE_NAME
FROM ALL_TABLES
WHERE OWNER = 'PLTTUX_ADMIN'
MINUS
SELECT TABLE_NAME
FROM ALL_CONSTRAINTS
WHERE OWNER = 'PLTTUX_ADMIN'
AND (CONSTRAINT_TYPE = 'P')
ORDER BY TABLE_NAME;
我相信在比较之前首先正确排序这些表是正确的方法。对于具有主键的表,我可以简单地按主键排序,但对于没有主键的其他表,我需要列出所有要排序的列。我发现这有用:
SELECT listagg(COLUMN_NAME,', ') WITHIN GROUP(ORDER BY COLUMN_NAME)
CSV
FROM ALL_TAB_COLUMNS
WHERE TABLE_NAME = 'NAME_OF_TABLE';
然后我可以使用逗号分隔列表:
SELECT *
FROM NAME_OF_TABLE
ORDER BY
(SELECT listagg(COLUMN_NAME,', ') WITHIN GROUP(ORDER BY COLUMN_NAME)
CSV
FROM ALL_TAB_COLUMNS
WHERE TABLE_NAME = 'NAME_OF_TABLE');
我的比较:
通常,我会使用相同的SQL命令获取两个数据库并为每个数据库获取ResultSet,然后继续执行while循环,其中rs1.next()和rs2.next()为true。
我可以通过添加“WHERE ROWNUM <= number_of_rows_returned”来编写代码以将我的SQL限制为某些行以进行百分比比较
这就是我不那么短的问题的根源所在:我是否以明显的次优方式完成所有这些工作?有没有更好的办法?有没有我应该听说过的工具?请帮助我:)我希望我已经分享了足够的想法...
按照以下步骤,
1.)在源数据库中创建数据库链接以连接将连接到目标数据库的数据库链接。
2.)使用MINUS set运算符比较两个表的数据。以下示例查询,
SELECT *
FROM table1
MINUS
SELECT *
FROM table1@dblink;
SELECT *
FROM table1@dblink
MINUS
SELECT *
FROM table1;
如果某些行返回,则存在差异。