SSIS 在大型ETL 开发中的性能调整(http://www.bridata.ca/blog/?p=927)

SSIS 的性能表现在实现大型 Data Warehouse 的过程是非常重要的,尤其是在数据量巨大的环境下。SSIS 的性能调整在很大程度上还是依赖于数据库性能和T-SQL的性能,因为归根结底它的内核还是SQL 语句,但是作为一个 ETL 的工具,它本身又具有与 T-SQL 和数据库性能调整不同的内容。本文将从各个角度探讨 SSIS 开发过程中性能优化的方法和技巧,这些方法和技巧未必适合于所有的条件和场合,但是它们所包含和策略将对任何的 SSIS 具有指导的作用。这个话题其实很大,估计一天两天也写不完,耐心看吧。

优化组件选择

SSIS 的最大优势在于图形化的、利于使用和维护的开发环境,而在提升方便性和可视化过程中却是以损失性能为代价的。比如说Data Flow 任务中的各种转换组件,使用起来非常方便和直观,但是它们在某些特殊的条件下却可以使用更为有效的其他控制流任务来替换。比如,我们的如果在SQL Server 数据表间做记录的ETL 处理,高效的 SQL 语句也许比使用各种数据流任务中的Transformation 要高效的多。看下面的例子:数据源表 A 中包括:ID,Name, DataofBirth, Address,Phone,Email; 数据源表 B 中包括 ID, Position。我们要把记录插入到数据目标表C 中:ID,Name,Address,Phone,Email, Position, 如果我们使用 Data Flow 任务来处理,结果可能是这样:

如果这种数据传输的过程中好涉及到其他的表或者数据转换,则需要更多的 Transaformation 组件。很显然这些操作都可以使用简单的 SQL 语句来实现:

INSERT INTO TableC SELECT a.ID, a.Name,a.DataofBirth,a.Address,a.Phone,a.Email,b.Position FROM TableA a LEFT JOIN TableB b ON a.ID = b.ID

而这个SQL 语句可以使用一个 Execute SQL 语句来实现,而它的性能却比使用一系列的 Data Transformation 要好得多。

优化数据源

  • Data Flow 中的数据源优化是一个经常被忽略的话题,不论是使用 ADO.NET 数据源还是OLE DB 数据源,开发人员经常简单地使用 ‘Table or View’ 作为数据源,这不是一个好习惯。在 Data Flow 的数据源中只使用必要的字段是优化 Data Flow 任务的重要原则。所以使用 SQL Command 要比直接地使用 Table or View 好得多,尤其是在 SQL Command 中可以使用SQL 函数来代替其他的 Transformation, 比如:数据类型转化、求和和 Look up 的。
  • 在使用 SQL Command 的时候也应该注意 SQL 语句的优化,比如最好不要使用诸如: SELECT * FROM myTable,应该使用 SELECT <Column List>,  FROM myTable, 即使选择表中所有的列,显性使用字段名要比使用 ‘*’ 性能好得多。
  • 尽可能使用 With (nolock) SQL Hint,使用 SELECT <Column list> FROM mytable with (nolock) 可以提高读取数据源的性能。
  • 当Look up 表和数据源表在同一个服务器或者数据库中的时候,在数据源的SQL Command 中使用 LEFT JOIN 要比使用 Look Up 更为简单是直接,但是前提必须是 Reference 表一定是个SQL 表。

合理使用Lookup

Lookup 是一个很常用的 Transformation, 它用来实现类似于SQL 中 LEFT JOIN 的功能,不同的是 Reference 表可以来自于任何数据源。在 Lookup 中影响性能最大的就是 Cache 模式,最常用的 Full Cache 模式下的OLD DB 连接,它将所有的Reference 表中的记录读到内存中,所以速度最快,但是条件是 Reference 表的记录不是很多,或者系统的内存足够大;另外一个处理大数据Reference 表的方法是使用 Full Cache 模式下的 Cache 文件连接,它是SSIS 2008 的新功能,它的优点是占用内存少,速度快,Cache 文件可以被多个数据流任务或者同一数据流任务中的不同进程所共享,但是前提必须是建立 Reference 表的Cache 文件,好在建立Cache 文件的过程很快。关于详细使用 Cache file lookup 的方法请参考我的另一篇文章:http://www.bridata.ca/blog/?p=233

使用 Bulk Insert 控制流任务

Bulk Insert 控制流任务是性能最好的控制流任务, 它其实就是BCP 命令的翻版。当使用文本文件作为数据源的时候,使用 Bulk Insert 任务要比使用 Data Flow 任务速度要快的多的多。

优化数据目标 (Destination)

数据流任务中数据目标的选择和优化直接影响到数据的写入操作。在使用SQL Server 作为数据目标(既将数据导入到 SQL Server)的时候有几个不同的选项:OLE DB, OLE DB with Fastload 和 SQL Server,  在选择和设置数据目标的时候使用下面的原则:

  • SQL Server Destination 速度最快,但是前提是运行 SSIS Package 的机器必须和 SQL Server 目标数据在同一台机器上。原因是它使用 Bulk Insert 来完成插入记录的操作,但是需要在本机内存中建立一个公共的内存区域来存储数据源。
  • 在不能使用SQL Server Destination 的情况下尽量使用 OLE DB with Fastload,它要比 OLE DB 快得多。它同样适用 Bulk Insert 来完成插入的操作,只不过它的数据源是使用 Openrowset.
  • 不论是使用 SQL Server Destination 还是使用 OLEDB with Fastload, 它们都有一个重要的选项值得注意:MaxInsertCommitSize,它用来指定 Commit 操作的 Batch 的尺寸,它的默认值是 0, 也就是说一个 Bulk Insert 只使用一个 Commit 命令,当为0的时候它的性能最好,但是前提是必须拥有足够的内存,否则也会在内存形成阻塞反而影响性能。
  • 当将大量的数据插入到目标表的时候,通常要先将目标表的Cluster 索引删除然后再将 Non Cluster 索引失效,在数据导入完成之后再重新建立索引,重建索引的时间要远远小于带索引导入浪费的时间。

使用 Kimball Slowly Changing Dimension 组件

当我们使用 SSIS 作为数据仓库的 ETL 处理的工具时,免不了使用 Slowly Changing Dimension 转化组件。但是由于它使用逐行比较和逐行Update 的机制,所以当处理记录数很大的维度表的时候它的速度却非常慢,于是很多人使用自己开发的 Transformtion 来代替它,其中一个我认为最好的替代品是 Kimball Slowly Changing Dimension 组件。它的下载地址是:http://kimballscd.codeplex.com/, 它的性能不但要优于 SSIS 自带的 Slowly Changing Dimension,而且还支持 Kimball SCD 中描述的其他功能,比如删除 Dimension 表中的记录和 Audit 功能等。下面是我使用 Kimball SCD 的一个屏幕截图:

 

你可能感兴趣的:(SSIS 在大型ETL 开发中的性能调整(http://www.bridata.ca/blog/?p=927))