我在 dtsx 包中有一个数据流,可以处理我需要处理的所有数据。最后,我需要执行一些清理任务。例如,假设以下结构:
如果所有 3 个案例的记录都为真,那么我想运行所有三个 OLE DB 命令。如果记录仅适用于案例 1,则它应该只运行案例 1。
我可以通过多播和 3 个单独的条件拆分(如下所示)来做到这一点,但我希望有一种更清洁的方式。有任何想法吗?
我在 dtsx 包中有一个数据流,可以处理我需要处理的所有数据。最后,我需要执行一些清理任务。例如,假设以下结构:
如果所有 3 个案例的记录都为真,那么我想运行所有三个 OLE DB 命令。如果记录仅适用于案例 1,则它应该只运行案例 1。
我可以通过多播和 3 个单独的条件拆分(如下所示)来做到这一点,但我希望有一种更清洁的方式。有任何想法吗?
使用多播和三个条件拆分是最容易实现的,也可能是最容易理解的。
设置为具有三个输出的转换的脚本组件可能是下一个最容易实现的 - 但它将涉及大量设置和一定程度的编码。数据流看起来会比较漂亮:
对于每个输出,确保将其设置Synchronous Input ID
为None
(以便您可以控制何时创建行);那么您需要在每个输出中复制每个输入列。脚本代码本身将如下所示:
public override void IncomingRows_ProcessInputRow(IncomingRowsBuffer Row)
{
if (Case1Logic(Row))
{
Case1OutputBuffer.AddRow();
Case1OutputBuffer.ProductId = Row.ProductID;
Case1OutputBuffer.Name = Row.Name;
// etc. for all columns
}
if (Case2Logic(Row))
{
Case2OutputBuffer.AddRow();
Case2OutputBuffer.ProductId = Row.ProductID;
Case2OutputBuffer.Name = Row.Name;
// etc. for all columns
}
if (Case3Logic(Row))
{
Case3OutputBuffer.AddRow();
Case3OutputBuffer.ProductId = Row.ProductID;
Case3OutputBuffer.Name = Row.Name;
// etc. for all columns
}
}
private bool Case1Logic(IncomingRowsBuffer Row)
{
// Whatever the Case 1 logic involves
}
private bool Case2Logic(IncomingRowsBuffer Row)
{
// Whatever the Case 2 logic involves
}
private bool Case3Logic(IncomingRowsBuffer Row)
{
// Whatever the Case 3 logic involves
}
当人们决定要更改列时,请保持最新状态!
如果这对您来说还不够麻烦,您可以编写自己的自定义转换。如何做到这一点的血淋淋的细节在MSDN中;可以说会涉及更多的代码。对于 SSIS 如何处理缓冲区管理,您还将了解比您想知道的更多,这反过来可以解释为什么开箱即用的条件拆分不允许您将同一行发送到多个输出。
最后,如果您想要一个看起来非常丑陋的解决方案,同时也是维护的噩梦,请尝试为每个案例组合构建一个带有一个输出的条件拆分。在您的每个 OLE 目标前面放置一个 Union All 转换。将Cases 1, 2 and 3
输出定向到三向多播,其中一个多播输出到三个联合所有转换中的每一个。条件拆分的Cases 1 and 2
、Cases 2 and 3
和Cases 1 and 3
输出将分别进行双向多播转换(这反过来将馈送到适当的联合全部),而Case 1
和Case 2
输出Case 3
将直接转到适当的联合全部。它看起来像这样:
总而言之,我认为您最初的想法是最简单的,也可能是最好的。
根据您对 C# 或 VB 的熟悉程度,您可以编写自己的转换,该转换本质上是将多播和条件拆分合二为一。将脚本组件添加到数据流中,它会询问您它是源、转换还是目标。选择转换,添加您的输入和三个输出,然后从那里开始。祝你好运!