我们的Azure Data Factory v2解决方案中有许多数据库表合并步骤 . 我们在Azure SQL Server DB的单个实例中合并表 . 源表和目标表位于不同的DB模式中 . 源被定义为单个表上的选择或两个表的连接 .
我怀疑从性能角度来看,下面描述的场景中哪一个更好 .
场景一(每桌)
存储过程活动调用执行所有工作的存储过程 . 管道中的Stored Procedure活动调用该存储过程 . 使用所有源数据挂起目标表 . 这种存储过程的一个例子:
create or alter procedure dwh.fill_lnk_cemvypdet_cemstr2c_table_with_stage_data as
merge
dwh.lnk_cemvypdet_cemstr2c as target
using
(select
t.sa_hashkey cemvypdet_hashkey,
t.sa_timestamp load_date,
t.sa_source record_source,
d.sa_hashkey cemstr2c_hashkey
from
egje.cemvypdet t
join
egje.cemstr2c d
on
t.id_mstr = d.id_mstr)
as source
on target.cemvypdet_hashkey = source.cemvypdet_hashkey
and target.cemstr2c_hashkey = source.cemstr2c_hashkey
when not matched then
insert(
cemvypdet_hashkey,
cemstr2c_hashkey,
record_source,
load_date,
last_seen_date)
values(
source.cemvypdet_hashkey,
source.cemstr2c_hashkey,
source.record_source,
source.load_date,
source.load_date)
when matched then
update set last_seen_date = source.load_date;
场景二(每行)
复制活动声明要在“目标”选项卡中调用的存储过程,以便该活动为源的每一行调用存储过程 .
create or alter procedure dwh.fill_lnk_cemvypdet_cemstr2c_subset_table_row_with_stage_data
@lnk_cemvypdet_cemstr2c_subset dwh.lnk_cemvypdet_cemstr2c_subset_type readonly
as
merge
dwh.lnk_cemvypdet_cemstr2c_subset as target
using
@lnk_cemvypdet_cemstr2c_subset
as source
on target.cemvypdet_hashkey = source.cemvypdet_hashkey
and target.cemstr2c_hashkey = source.cemstr2c_hashkey
when not matched then
insert(
hashkey,
cemvypdet_hashkey,
cemstr2c_hashkey,
record_source,
load_date,
last_seen_date)
values(
source.hashkey,
source.cemvypdet_hashkey,
source.cemstr2c_hashkey,
source.record_source,
source.load_date,
source.load_date)
when matched then
update set last_seen_date = source.load_date;
类型@ lnk_cemvypdet_cemstr2c_subset被定义为遵循目标表结构的表类型 .
1 回答
场景1应该具有更好的性能,但需要考虑以下优化:
在源表中的连接列上创建唯一且覆盖的索引 .
在目标表的连接列上创建唯一的聚簇索引 .
参数化ON子句和WHEN子句中的所有文字值 .
使用OFFSET和ROWS FETCH NEXT合并从源到目标表的数据子集,或者通过在源或目标上定义返回已过滤行的视图并将视图作为源表或目标表引用 . 此外,建议不要使用TOP子句的WITH子句来过滤源表或目标表中的行,因为它们可能会生成不正确的结果 .
要进一步优化合并操作,请尝试不同的批量大小 . Here是原因 .