SQL Server Merge Replication的复杂过滤器

时间:2015-07-23 09:43:15

标签: sql sql-server filter merge-replication

我们在SQL Server 2012数据库中有一个存储树状结构的表。为了我的问题简化,它具有以下格式:

    Id int identity,
    ParentId int,
    GroupId int

表的每个记录表示由Id标识的对象。对象在同一个表中可能有也可能没有父对象,例如 object.ParentId = parentObject.Id 。根对象具有 ParentId = NULL 。有多个根对象,因此该表实际上存储了多个树。 重要的是树深度不固定,即理论上可以有一个对象的任何数量的祖先世代。 GroupId 是根对象的属性;理论上,根对象的子节点中没有一个必须具有 GroupId<> NULL ;可以假设任何子项具有与其根对象相同的 GroupId 值。

具有两个根(一个祖父母和一个父母),一个非根父母/子女和4个子根的样本表:

    Id       ParentId    GroupId
    ----------------------------------------------------------
    1        NULL          200           root grandparent
    2        1             NULL          non-root parent/child
    3        2             NULL          child
    4        2             NULL          child
    5        NULL          300           root parent
    6        5             NULL          child
    7        5             NULL          child

该表未规范化,即没有单独的{root_object:group}表。但是,我不认为规范化表格会有助于解决问题。

现在问题。我们需要将上表(主表)中的合并复制设置为另一个DB中相同格式的表。我们只需要复制具有某个固定的 GroupId 值的Master表的那些行,例如在上面的例子中有200个。如果我们确保根对象的所有后代对象中的 GroupId 在表中具有与根对象本身相同的值,那将是微不足道的。该表如下所示:

    Id       ParentId    GroupId
    ----------------------------------------------------------
    1        NULL          200            root grandparent
    2        1             200            non-root parent/child
    3        2             200            child
    4        2             200            child
    5        NULL          300            root parent
    6        5             300            child
    7        5             300            child

过滤器看起来像这样:

    WHERE GroupId = 200

但是出于性能方面的考虑,我们希望尽可能避免为后代对象填充 GroupId ,因为从上面必须清楚, GroupId 是通过存储过程或UDF可以很容易地推导出后代对象(只需要向上移动树直到 ParentId = NULL )。 问题是,我不知道如何在合并复制过滤器中实现这一点:它只允许 WHERE 条件和连接。一般来说,我对合并复制的连接运气不太好,但是这里我们有更复杂的算法,因为每个对象的树级数可能不同。 合并复制不允许使用UDF ...

1 个答案:

答案 0 :(得分:0)

我尝试过使用UDF并且已经有效了! 我之前尝试过,但当时失败了,我不记得为什么。现在我想我可能没有将UDF添加到订阅数据库,只添加到发布数据库......