2

我最近犯了一个代价高昂且令人尴尬的错误,如果它再次发生,我会很生气。我希望你能帮助我......这就是发生的事情。

在对 PROD 的部署中,其中一个步骤是确保所有DEV.code_mapping表行都存在于PROD.code_mapping表中。

为此,我运行了以下查询(Oracle 11g)。我希望它显示PROD.code_mappingDEV.code_mapping存在的每一行。

select * FROM code_mapping D 
where D.source_system_id = '&LHDNUMBER'
and not exists
    (select 1 from
    dm.code_mapping@PROD_CHECK P where
    D.mapping_definition_id = P.mapping_definition_id and
    D.cdm_code = P.cdm_code and
    D.source_system_code = P.source_system_code);

查询返回零个结果。

我错误地得出结论,每一行都DEV.code_mapping存在于PROD.code_mapping.

事实证明,实际上PROD.code_mapping表中不存在任何行。查询不知何故没有接受。我认为这可能是因为此查询无法针对 PROD 中的空值进行评估,但NVL([column],'null')似乎没有多少语句可以使这项工作。

我怎样才能使这项工作?

还:

除了查询更正本身之外,我欢迎您为此类工作提供任何最佳实践指针。我真的不想再像这样开始直播了。

4

2 回答 2

3

就个人而言,我会使用MINUS

SELECT *
  FROM code_mapping
 WHERE soure_system_id = '&LHDNUMBER'
MINUS
SELECT *
  FROM dm.code_mapping@prod_check

MINUS自动处理NULL比较(NULL源上的 a 自动匹配NULL目标上的 a)。

如果要列出两个表之间的所有差异(即列出 dev 但不存在 prod 和 prod 但不存在 dev 的所有行),可以添加 UNION ALL

(SELECT a.*, 'In dev but not prod' descriptio
   FROM dev_table a
 MINUS 
 SELECT a.*, 'In dev but not prod' description
   FROM prod_table a)
UNION ALL
(SELECT a.*, 'In prod but not dev' descriptio
   FROM prod_table a
 MINUS 
 SELECT a.*, 'In prod but not dev' description
   FROM dev_table a)
于 2013-10-31T23:27:32.650 回答
3

使用 LEFT JOIN 并且 myProdField 为空。

因此,对于您的查询,如果我没看错,您将有:

SELECT D.mapping_definition_id, D.cdm_code, D.source_system_code FROM code_mapping D
LEFT JOIN dm.code_mapping@PROD_CHECK P
  ON D.mapping_definition_id = P.mapping_definition_id
    AND D.cdm_code = P.cdm_code
    AND D.source_system_code = P.source_system_code
WHERE P.mapping_definition_id IS NULL

无论如何,这是一般的想法。除非满足所有三个条件,否则它将不匹配。因此,任何区别都会为您提供一个 P 字段为空的行,包括您正在过滤的 P.mapping_definition_id。因此,这将为您提供 DEV 中与 PROD 中不完全匹配的每一行。

至于最佳实践指南,确保您的部署完全按照您的计划进行的最安全方法是在相同的环境中进行实践。如果您有能力设置一个镜像生产的预生产环境,您可以先在那里测试部署,以确保它完成了您期望的工作。然后完全重复生产。

于 2013-11-01T22:53:48.550 回答