首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >基于复合主键值的增量数据读取

问基于复合主键值的增量数据读取
EN

Stack Overflow用户
提问于 2018-10-03 11:54:38
回答 2查看 384关注 0票数 0

我有一个OLTP (源),从这里数据必须移动到DWH(目的地)的增量基础上。源表在Loan_id,AssetID上有一个复合主键,如下所示。

代码语言:javascript
复制
LOAN_ID, ASSETID, REC_STATUS
'12848','13170', 'F'

如果它是一个单一的col主键,那么我将在目标处检查列的最大值,然后从主键值大于目标处的最大值的源读取所有记录,但是由于它是一个复合主键,这是行不通的。

你知道如何使用this查询来完成这个任务吗?

规范:源是MYSQL,目标是MSSQL 2012。连接是使用链接服务器进行的。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2018-10-04 19:56:29

有几件事你可以试试。处理链接服务器而不知道设置的具体细节以及数据量,性能可能是一个问题。

如果您不担心现有记录或删除的更改,那么一个简单的左外部联接将为您获得尚未插入到目的地的任何记录:

代码语言:javascript
复制
SELECT          [s].[LOAD_ID]
              , [s].[ASSETID]
              , [s].[REC_STATUS]
FROM            [LinkedServer].[Database].[schema].[SourceTable] [s]
LEFT OUTER JOIN [DestinationTable] [d]
    ON [s].[LOAN_ID] = [d].[LOAN_ID]
       AND [s].[ASSETID] = [d].[ASSETID]
WHERE           [d].[LOAN_ID] IS NULL;

如果您担心更改,您仍然可以使用左外部查找目标中的NULL或字段值的差异,但是您需要一个额外的update语句。

代码语言:javascript
复制
SELECT          [s].[LOAD_ID]
              , [s].[ASSETID]
              , [s].[REC_STATUS]
FROM            [LinkedServer].[Database].[schema].[SourceTable] [s]
LEFT OUTER JOIN [DestinationTable] [d]
    ON [s].[LOAN_ID] = [d].[LOAN_ID]
       AND [s].[ASSETID] = [d].[ASSETID]
WHERE           [d].[LOAN_ID] IS NULL --Records from source not in destination
                OR (
                        --This evaluates those in the destination, but then checks for changes in field values.
                       [d].[LOAN_ID] IS NOT NULL
                       AND (
                               [s].[REC_STATUS] <> [d].[REC_STATUS]
                               OR [s].[SomOtherField] <> [d].[SomeOtherField]
                           )
                   );

--The above insert into some landing or staging table on the destination side and then you could do a MERGE.

如果我们需要担心删除。从源中删除了一条记录,您不希望它再出现在目的地。翻转左侧外部以查找目标中不再位于源中的记录:

代码语言:javascript
复制
DELETE [d]
FROM           [DestinationTable] [d]
LEFT OUTER JOIN [LinkedServer].[Database].[schema].[SourceTable] [s]
    ON [s].[LOAN_ID] = [d].[LOAN_ID]
   AND [s].[ASSETID] = [d].[ASSETID]
WHERE           [s].[LOAD_ID] IS NULL;

您可以尝试使用合并来完成所有这些操作。在链接的服务器上尝试合并,或将所有源记录带到land/stage表中的目标,然后在那里进行合并。下面是一个试图在链接服务器上运行的示例。

代码语言:javascript
复制
MERGE [DestinationTable] [t]
USING [LinkedServer].[Database].[schema].[SourceTable] [s]
ON [s].[LOAN_ID] = [d].[LOAN_ID]
   AND [s].[ASSETID] = [d].[ASSETID]
WHEN MATCHED THEN UPDATE SET [REC_STATUS] = [s].[REC_STATUS]
WHEN NOT MATCHED BY TARGET THEN INSERT (
                                           [REC_STATUS]
                                       )
                                VALUES ( [s].[REC_STATUS] )
WHEN NOT MATCHED BY SOURCE THEN DELETE;

在处理合并时,请注意以下语句:

代码语言:javascript
复制
WHEN NOT MATCHED BY SOURCE THEN DELETE;

如果不使用整个记录集,则可能会丢失目的地中的记录。例如,您已经将从源中提取的结果集限制在一个暂存表中,您现在将暂存表与最终目的地合并,在目标中任何外部的内容都将被删除。你可以通过限制你的目标通过一个CTE,谷歌:“合并到cte作为目标”。这是如果你有一个日期你可以过滤。

如果您有日期列,这总是有帮助的,特别是在插入或更新新记录时,会出现某种更改/更新日期列。然后你可以过滤你的源,只有那些你关心的记录。

票数 2
EN

Stack Overflow用户

发布于 2018-10-03 13:29:22

增量负载通常有一个日期驱动它们。

您可以在查找中使用复合键。这一问题已得到多次答复。

添加查找并更改测试以重定向任何匹配(默认为失败)。

基本上,您需要检查目标中是否存在密钥。

如果键存在,那么它就是一个更新(匹配)。

如果键不存在(不匹配),则为insert。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/52626486

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档