我正在为一个仓库实现一个新的方法。这个新方法包括在源表和目标表之间执行增量加载(插入,更新或删除)。
所有的表都运行得很好,除了一个表,它的源代码有超过300万行,正如你在下面的图像中看到的,它只是开始运行,但从来没有完成。可能我没有用正确的方式做更新,或者有另一种方式来做。
下面是我的SSIS软件包的一些图片:
突出显示的对象是它挂起的位置。
这是我调用来更新表的存储过程:
ALTER PROCEDURE [dbo].[UpdateDim_A]
@ID INT,
@FileDataID INT
,@CategoryID SMALLINT
,@FirstName VARCHAR(50)
,@LastName VARCHAR(50)
,@Company VARCHAR(100)
,@Email VARCHAR(250) AS BEGIN
SET NOCOUNT ON;
BEGIN TRAN
UPDATE DIM_A
SET
[FileDataID] = @FileDataID,
[CategoryID] = @CategoryID,
[FirstName] = @FirstName,
[LastName] = @LastName,
[Company] = @Company,
[Email] = @Email
WHERE PartyID=@ID
COMMIT TRAN; END
**注意:**我已尝试删除约束和索引并将数据库的恢复模式更改为简单。
任何帮助都将不胜感激。
应用@Prabhat G提供的解决方案后,我的软件包看起来是这样的,运行时间为39秒(平均值)!!!
内部尺寸_A数据流
3条答案
按热度按时间yizd12fk1#
遵循这两个性能增强器,你会避免你的瓶颈。
1.删除
sort
转换。在源中,提取数据时使用order by
sql。原因是sort
在排序前占用内存中的所有记录。无论是增量加载还是完全加载,您都不希望这样。1.在更新的最后一步中,引入另一个临时表而不是
update records oledb command
,它将是Dim表的副本。在此新临时表中插入所有匹配记录后,退出数据流任务并创建EXECUTE SQL TASK
,它将根据联接ID/条件简单地更新Dim表。原因是,oledb命令逐行命中。始终首选使用
Execute SQL Task
作为批处理进行更新。**编辑:**根据注解,为了仅更新
Execute SQL Task
中已更改的行,请在where子句中添加条件:k7fdbhmy2#
所以你的问题实际上很简单,你使用的方法是对返回的每一行执行存储过程。如果你有9961行要更新(如图所示),它将分别运行9961次语句。如果你查看SQL服务器上运行的活动查询,你可能会看到该过程一遍又一遍地执行。
为了加快速度,您应该将数据转储到一个临时表中,然后在您的包中进一步使用执行SQL任务来运行标准SQL更新,这将运行得更快。
mspsb9vt3#
问题是您试图在数据流中执行存储过程。正确的SqlCommand将是显式UPDATE查询,然后将SSIS中的列Map到要更新的表中的列。
注意:@Id需要作为列包含在数据流中。
你应该考虑的最后一件事,正如赞内正确指出的那样:应仅更新已更改的行。因此,应在数据流中添加条件性拆分转换,该转换将检查新源行中是否有任何列与现有表行不同。只有不同的行才应发送到OLE DB命令,其余行可以忽略。